aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/CMakeLists.txt140
-rw-r--r--src/StaticStack.h38
-rw-r--r--src/components/alarm/AlarmController.cpp2
-rw-r--r--src/components/alarm/AlarmController.h6
-rw-r--r--src/components/battery/BatteryController.cpp30
-rw-r--r--src/components/battery/BatteryController.h7
-rw-r--r--src/components/ble/AlertNotificationClient.cpp6
-rw-r--r--src/components/ble/AlertNotificationClient.h2
-rw-r--r--src/components/ble/AlertNotificationService.cpp6
-rw-r--r--src/components/ble/AlertNotificationService.h3
-rw-r--r--src/components/ble/BatteryInformationService.cpp9
-rw-r--r--src/components/ble/BatteryInformationService.h4
-rw-r--r--src/components/ble/BleController.h8
-rw-r--r--src/components/ble/CurrentTimeClient.cpp20
-rw-r--r--src/components/ble/CurrentTimeClient.h13
-rw-r--r--src/components/ble/CurrentTimeService.cpp97
-rw-r--r--src/components/ble/CurrentTimeService.h27
-rw-r--r--src/components/ble/DeviceInformationService.cpp6
-rw-r--r--src/components/ble/DeviceInformationService.h4
-rw-r--r--src/components/ble/DfuService.h4
-rw-r--r--src/components/ble/FSService.h6
-rw-r--r--src/components/ble/HeartRateService.cpp14
-rw-r--r--src/components/ble/HeartRateService.h8
-rw-r--r--src/components/ble/ImmediateAlertService.cpp6
-rw-r--r--src/components/ble/ImmediateAlertService.h4
-rw-r--r--src/components/ble/MotionService.cpp13
-rw-r--r--src/components/ble/MotionService.h8
-rw-r--r--src/components/ble/MusicService.cpp6
-rw-r--r--src/components/ble/MusicService.h3
-rw-r--r--src/components/ble/NavigationService.cpp8
-rw-r--r--src/components/ble/NavigationService.h3
-rw-r--r--src/components/ble/NimbleController.cpp12
-rw-r--r--src/components/ble/NimbleController.h3
-rw-r--r--src/components/ble/NotificationManager.h2
-rw-r--r--src/components/ble/weather/WeatherService.cpp20
-rw-r--r--src/components/ble/weather/WeatherService.h3
-rw-r--r--src/components/datetime/DateTimeController.cpp16
-rw-r--r--src/components/datetime/DateTimeController.h72
-rw-r--r--src/components/fs/FS.cpp11
-rw-r--r--src/components/fs/FS.h1
-rw-r--r--src/components/gfx/Gfx.h3
-rw-r--r--src/components/heartrate/HeartRateController.h4
-rw-r--r--src/components/heartrate/Ppg.cpp38
-rw-r--r--src/components/heartrate/Ppg.h6
-rw-r--r--src/components/heartrate/Ptagc.cpp8
-rw-r--r--src/components/motion/MotionController.cpp8
-rw-r--r--src/components/motion/MotionController.h5
-rw-r--r--src/components/motor/MotorController.cpp2
-rw-r--r--src/components/settings/Settings.h13
-rw-r--r--src/components/timer/TimerController.h1
-rw-r--r--src/components/utility/LinearApproximation.h41
-rw-r--r--src/displayapp/Apps.h3
-rw-r--r--src/displayapp/DisplayApp.cpp133
-rw-r--r--src/displayapp/DisplayApp.h12
-rw-r--r--src/displayapp/DisplayAppRecovery.cpp32
-rw-r--r--src/displayapp/DisplayAppRecovery.h3
-rw-r--r--src/displayapp/DummyLittleVgl.h5
-rw-r--r--src/displayapp/InfiniTimeTheme.cpp81
-rw-r--r--src/displayapp/InfiniTimeTheme.h8
-rw-r--r--src/displayapp/LittleVgl.cpp21
-rw-r--r--src/displayapp/LittleVgl.h3
-rw-r--r--src/displayapp/Messages.h1
-rw-r--r--src/displayapp/screens/BatteryInfo.cpp2
-rw-r--r--src/displayapp/screens/CheckboxList.cpp4
-rw-r--r--src/displayapp/screens/CheckboxList.h1
-rw-r--r--src/displayapp/screens/FirmwareUpdate.h1
-rw-r--r--src/displayapp/screens/FirmwareValidation.cpp6
-rw-r--r--src/displayapp/screens/HeartRate.cpp8
-rw-r--r--src/displayapp/screens/HeartRate.h1
-rw-r--r--src/displayapp/screens/InfiniPaint.h1
-rw-r--r--src/displayapp/screens/List.cpp50
-rw-r--r--src/displayapp/screens/Metronome.cpp3
-rw-r--r--src/displayapp/screens/Motion.cpp12
-rw-r--r--src/displayapp/screens/Notifications.cpp55
-rw-r--r--src/displayapp/screens/Notifications.h5
-rw-r--r--src/displayapp/screens/Paddle.cpp4
-rw-r--r--src/displayapp/screens/Paddle.h1
-rw-r--r--src/displayapp/screens/Screen.h11
-rw-r--r--src/displayapp/screens/ScreenList.h1
-rw-r--r--src/displayapp/screens/Steps.h1
-rw-r--r--src/displayapp/screens/SystemInfo.cpp4
-rw-r--r--src/displayapp/screens/Tile.cpp8
-rw-r--r--src/displayapp/screens/Timer.h5
-rw-r--r--src/displayapp/screens/Twos.h1
-rw-r--r--src/displayapp/screens/WatchFaceAnalog.cpp22
-rw-r--r--src/displayapp/screens/WatchFaceAnalog.h1
-rw-r--r--src/displayapp/screens/WatchFaceCasioStyleG7710.cpp1
-rw-r--r--src/displayapp/screens/WatchFaceInfineat.cpp281
-rw-r--r--src/displayapp/screens/WatchFaceInfineat.h34
-rw-r--r--src/displayapp/screens/WatchFacePineTimeStyle.h2
-rw-r--r--src/displayapp/screens/WatchFaceTerminal.cpp2
-rw-r--r--src/displayapp/screens/Weather.cpp1
-rw-r--r--src/displayapp/screens/Weather.h1
-rw-r--r--src/displayapp/screens/settings/SettingBluetooth.cpp112
-rw-r--r--src/displayapp/screens/settings/SettingBluetooth.h9
-rw-r--r--src/displayapp/screens/settings/SettingChimes.cpp98
-rw-r--r--src/displayapp/screens/settings/SettingChimes.h17
-rw-r--r--src/displayapp/screens/settings/SettingSetDate.cpp16
-rw-r--r--src/displayapp/screens/settings/SettingSetDate.h7
-rw-r--r--src/displayapp/screens/settings/SettingSetDateTime.cpp54
-rw-r--r--src/displayapp/screens/settings/SettingSetDateTime.h32
-rw-r--r--src/displayapp/screens/settings/SettingSetTime.cpp14
-rw-r--r--src/displayapp/screens/settings/SettingSetTime.h6
-rw-r--r--src/displayapp/screens/settings/SettingShakeThreshold.cpp4
-rw-r--r--src/displayapp/screens/settings/SettingShakeThreshold.h1
-rw-r--r--src/displayapp/screens/settings/SettingTimeFormat.cpp106
-rw-r--r--src/displayapp/screens/settings/SettingTimeFormat.h7
-rw-r--r--src/displayapp/screens/settings/SettingWakeUp.cpp87
-rw-r--r--src/displayapp/screens/settings/SettingWakeUp.h23
-rw-r--r--src/displayapp/screens/settings/SettingWatchFace.cpp56
-rw-r--r--src/displayapp/screens/settings/SettingWatchFace.h25
-rw-r--r--src/displayapp/screens/settings/Settings.h17
-rw-r--r--src/displayapp/widgets/Counter.cpp4
-rw-r--r--src/displayapp/widgets/DotIndicator.cpp28
-rw-r--r--src/displayapp/widgets/DotIndicator.h18
-rw-r--r--src/displayapp/widgets/StatusIcons.h2
-rw-r--r--src/drivers/Bma421.cpp4
-rw-r--r--src/drivers/Bma421.h3
-rw-r--r--src/drivers/Cst816s.h3
-rw-r--r--src/drivers/DebugPins.cpp2
-rw-r--r--src/drivers/DebugPins.h24
-rw-r--r--src/drivers/Hrs3300.cpp1
-rw-r--r--src/drivers/SpiMaster.cpp7
-rw-r--r--src/drivers/SpiMaster.h6
-rw-r--r--src/drivers/SpiNorFlash.h1
-rw-r--r--src/drivers/St7789.h1
-rw-r--r--src/drivers/Watchdog.h3
-rw-r--r--src/heartratetask/HeartRateTask.cpp35
-rw-r--r--src/heartratetask/HeartRateTask.h2
-rw-r--r--src/logging/DummyLogger.h1
-rw-r--r--src/main.cpp39
-rw-r--r--src/recoveryLoader.cpp3
-rw-r--r--src/resources/fonts.json2
-rw-r--r--src/systemtask/Messages.h4
-rw-r--r--src/systemtask/SystemTask.cpp32
-rw-r--r--src/systemtask/SystemTask.h3
-rw-r--r--src/touchhandler/TouchHandler.h5
137 files changed, 1357 insertions, 1179 deletions
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index ce365dd1..95846a9b 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -407,6 +407,7 @@ list(APPEND SOURCE_FILES
displayapp/Colors.cpp
displayapp/widgets/Counter.cpp
displayapp/widgets/PageIndicator.cpp
+ displayapp/widgets/DotIndicator.cpp
displayapp/widgets/StatusIcons.cpp
## Settings
@@ -417,6 +418,7 @@ list(APPEND SOURCE_FILES
displayapp/screens/settings/SettingWakeUp.cpp
displayapp/screens/settings/SettingDisplay.cpp
displayapp/screens/settings/SettingSteps.cpp
+ displayapp/screens/settings/SettingSetDateTime.cpp
displayapp/screens/settings/SettingSetDate.cpp
displayapp/screens/settings/SettingSetTime.cpp
displayapp/screens/settings/SettingChimes.cpp
@@ -440,7 +442,6 @@ list(APPEND SOURCE_FILES
drivers/SpiMaster.cpp
drivers/Spi.cpp
drivers/Watchdog.cpp
- drivers/DebugPins.cpp
drivers/InternalFlash.cpp
drivers/Hrs3300.cpp
drivers/Bma421.cpp
@@ -507,7 +508,6 @@ list(APPEND RECOVERY_SOURCE_FILES
drivers/SpiMaster.cpp
drivers/Spi.cpp
drivers/Watchdog.cpp
- drivers/DebugPins.cpp
drivers/InternalFlash.cpp
drivers/Hrs3300.cpp
drivers/Bma421.cpp
@@ -616,13 +616,13 @@ set(INCLUDE_FILES
displayapp/Colors.h
displayapp/widgets/Counter.h
displayapp/widgets/PageIndicator.h
+ displayapp/widgets/DotIndicator.h
displayapp/widgets/StatusIcons.h
drivers/St7789.h
drivers/SpiNorFlash.h
drivers/SpiMaster.h
drivers/Spi.h
drivers/Watchdog.h
- drivers/DebugPins.h
drivers/InternalFlash.h
drivers/Hrs3300.h
drivers/PinMap.h
@@ -686,6 +686,8 @@ include_directories(
${CMAKE_BINARY_DIR}/src # include generated files like Version.h
.
../
+)
+include_directories(SYSTEM
libs/
FreeRTOS/
libs/date/include
@@ -778,7 +780,12 @@ link_directories(
)
-set(COMMON_FLAGS -MP -MD -mthumb -mabi=aapcs -Wall -Wextra -Warray-bounds=2 -Wformat=2 -Wformat-overflow=2 -Wformat-truncation=2 -Wformat-nonliteral -ftree-vrp -Wno-unused-parameter -Wno-missing-field-initializers -Wno-unknown-pragmas -Wno-expansion-to-defined -g3 -ffunction-sections -fdata-sections -fno-strict-aliasing -fno-builtin --short-enums -mcpu=cortex-m4 -mfloat-abi=hard -mfpu=fpv4-sp-d16 -Wreturn-type -Werror=return-type -fstack-usage -fno-exceptions -fno-non-call-exceptions)
+set(COMMON_FLAGS -MP -MD -mthumb -mabi=aapcs -ftree-vrp -ffunction-sections -fdata-sections -fno-strict-aliasing -fno-builtin -fshort-enums -mcpu=cortex-m4 -mfloat-abi=hard -mfpu=fpv4-sp-d16 -fstack-usage -fno-exceptions -fno-non-call-exceptions)
+set(WARNING_FLAGS -Wall -Wextra -Warray-bounds=2 -Wformat=2 -Wformat-overflow=2 -Wformat-truncation=2 -Wformat-nonliteral -Wno-missing-field-initializers -Wno-unknown-pragmas -Wno-expansion-to-defined -Wreturn-type -Werror=return-type)
+set(DEBUG_FLAGS -Og -g3)
+set(RELEASE_FLAGS -Os)
+set(CXX_FLAGS -fno-rtti)
+set(ASM_FLAGS -x assembler-with-cpp)
add_definitions(-DCONFIG_GPIO_AS_PINRESET)
add_definitions(-DNIMBLE_CFG_CONTROLLER)
add_definitions(-DOS_CPUTIME_FREQ)
@@ -843,11 +850,11 @@ endif()
add_subdirectory(displayapp/fonts)
target_compile_options(infinitime_fonts PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
# NRF SDK
@@ -855,11 +862,12 @@ add_library(nrf-sdk STATIC ${SDK_SOURCE_FILES})
target_include_directories(nrf-sdk SYSTEM PUBLIC . ../)
target_include_directories(nrf-sdk SYSTEM PUBLIC ${INCLUDES_FROM_LIBS})
target_compile_options(nrf-sdk PRIVATE
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Wno-expansion-to-defined -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Wno-expansion-to-defined -O3>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Wno-expansion-to-defined -Og -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Wno-expansion-to-defined -O3 -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
+ -O3
)
# NimBLE
@@ -867,11 +875,11 @@ add_library(nimble STATIC ${NIMBLE_SRC} ${TINYCRYPT_SRC})
target_include_directories(nimble SYSTEM PUBLIC . ../)
target_include_directories(nimble SYSTEM PUBLIC ${INCLUDES_FROM_LIBS})
target_compile_options(nimble PRIVATE
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -Wno-unused-but-set-variable -Wno-maybe-uninitialized>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -Wno-unused-but-set-variable -Wno-maybe-uninitialized>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -Wno-unused-but-set-variable -Wno-maybe-uninitialized -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -Wno-unused-but-set-variable -Wno-maybe-uninitialized -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
# lvgl
@@ -879,11 +887,11 @@ add_library(lvgl STATIC ${LVGL_SRC})
target_include_directories(lvgl SYSTEM PUBLIC . ../)
target_include_directories(lvgl SYSTEM PUBLIC ${INCLUDES_FROM_LIBS})
target_compile_options(lvgl PRIVATE
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
# QCBOR
@@ -900,9 +908,11 @@ target_compile_definitions(QCBOR PUBLIC QCBOR_DISABLE_UNCOMMON_TAGS)
target_compile_definitions(QCBOR PUBLIC USEFULBUF_CONFIG_LITTLE_ENDIAN)
set_target_properties(QCBOR PROPERTIES LINKER_LANGUAGE C)
target_compile_options(QCBOR PRIVATE
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -O0 -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -O3>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
+ -O3
)
# LITTLEFS_SRC
@@ -910,11 +920,11 @@ add_library(littlefs STATIC ${LITTLEFS_SRC})
target_include_directories(littlefs SYSTEM PUBLIC . ../)
target_include_directories(littlefs SYSTEM PUBLIC ${INCLUDES_FROM_LIBS})
target_compile_options(littlefs PRIVATE
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Wno-unused-function -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Wno-unused-function -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Wno-unused-function -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Wno-unused-function -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
# Build autonomous binary (without support for bootloader)
@@ -925,11 +935,12 @@ add_executable(${EXECUTABLE_NAME} ${SOURCE_FILES})
set_target_properties(${EXECUTABLE_NAME} PROPERTIES OUTPUT_NAME ${EXECUTABLE_FILE_NAME})
target_link_libraries(${EXECUTABLE_NAME} nimble nrf-sdk lvgl littlefs QCBOR infinitime_fonts)
target_compile_options(${EXECUTABLE_NAME} PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Wextra -Wformat -Wno-missing-field-initializers -Wno-unused-parameter -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Wextra -Wformat -Wno-missing-field-initializers -Wno-unused-parameter -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Wextra -Wformat -Wno-missing-field-initializers -Wno-unused-parameter -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Wextra -Wformat -Wno-missing-field-initializers -Wno-unused-parameter -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ ${WARNING_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
set_target_properties(${EXECUTABLE_NAME} PROPERTIES
@@ -959,11 +970,12 @@ add_executable(${EXECUTABLE_MCUBOOT_NAME} ${SOURCE_FILES})
target_link_libraries(${EXECUTABLE_MCUBOOT_NAME} nimble nrf-sdk lvgl littlefs QCBOR infinitime_fonts)
set_target_properties(${EXECUTABLE_MCUBOOT_NAME} PROPERTIES OUTPUT_NAME ${EXECUTABLE_MCUBOOT_FILE_NAME})
target_compile_options(${EXECUTABLE_MCUBOOT_NAME} PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ ${WARNING_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
set_target_properties(${EXECUTABLE_MCUBOOT_NAME} PROPERTIES
@@ -1001,11 +1013,12 @@ target_link_libraries(${EXECUTABLE_RECOVERY_NAME} nimble nrf-sdk littlefs QCBOR
set_target_properties(${EXECUTABLE_RECOVERY_NAME} PROPERTIES OUTPUT_NAME ${EXECUTABLE_RECOVERY_FILE_NAME})
target_compile_definitions(${EXECUTABLE_RECOVERY_NAME} PUBLIC "PINETIME_IS_RECOVERY")
target_compile_options(${EXECUTABLE_RECOVERY_NAME} PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ ${WARNING_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
set_target_properties(${EXECUTABLE_RECOVERY_NAME} PROPERTIES
@@ -1032,11 +1045,12 @@ target_link_libraries(${EXECUTABLE_RECOVERY_MCUBOOT_NAME} nimble nrf-sdk littlef
set_target_properties(${EXECUTABLE_RECOVERY_MCUBOOT_NAME} PROPERTIES OUTPUT_NAME ${EXECUTABLE_RECOVERY_MCUBOOT_FILE_NAME})
target_compile_definitions(${EXECUTABLE_RECOVERY_MCUBOOT_NAME} PUBLIC "PINETIME_IS_RECOVERY")
target_compile_options(${EXECUTABLE_RECOVERY_MCUBOOT_NAME} PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ ${WARNING_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
set_target_properties(${EXECUTABLE_RECOVERY_MCUBOOT_NAME} PROPERTIES
@@ -1070,11 +1084,12 @@ add_executable(${EXECUTABLE_RECOVERYLOADER_NAME} ${RECOVERYLOADER_SOURCE_FILES})
target_link_libraries(${EXECUTABLE_RECOVERYLOADER_NAME} nrf-sdk QCBOR infinitime_fonts)
set_target_properties(${EXECUTABLE_RECOVERYLOADER_NAME} PROPERTIES OUTPUT_NAME ${EXECUTABLE_RECOVERYLOADER_FILE_NAME})
target_compile_options(${EXECUTABLE_RECOVERYLOADER_NAME} PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ ${WARNING_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
target_include_directories(${EXECUTABLE_RECOVERYLOADER_NAME} PUBLIC
$<BUILD_INTERFACE:${CMAKE_BINARY_DIR}/src>
@@ -1104,11 +1119,12 @@ add_executable(${EXECUTABLE_MCUBOOT_RECOVERYLOADER_NAME} ${RECOVERYLOADER_SOURCE
target_link_libraries(${EXECUTABLE_MCUBOOT_RECOVERYLOADER_NAME} nrf-sdk QCBOR infinitime_fonts)
set_target_properties(${EXECUTABLE_MCUBOOT_RECOVERYLOADER_NAME} PROPERTIES OUTPUT_NAME ${EXECUTABLE_MCUBOOT_RECOVERYLOADER_FILE_NAME})
target_compile_options(${EXECUTABLE_MCUBOOT_RECOVERYLOADER_NAME} PUBLIC
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3>
- $<$<AND:$<COMPILE_LANGUAGE:C>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:DEBUG>>: ${COMMON_FLAGS} -Og -g3 -fno-rtti>
- $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CONFIG:RELEASE>>: ${COMMON_FLAGS} -Os -fno-rtti>
- $<$<COMPILE_LANGUAGE:ASM>: -MP -MD -x assembler-with-cpp>
+ ${COMMON_FLAGS}
+ ${WARNING_FLAGS}
+ $<$<CONFIG:DEBUG>: ${DEBUG_FLAGS}>
+ $<$<CONFIG:RELEASE>: ${RELEASE_FLAGS}>
+ $<$<COMPILE_LANGUAGE:CXX>: ${CXX_FLAGS}>
+ $<$<COMPILE_LANGUAGE:ASM>: ${ASM_FLAGS}>
)
target_include_directories(${EXECUTABLE_MCUBOOT_RECOVERYLOADER_NAME} PUBLIC
$<BUILD_INTERFACE:${CMAKE_BINARY_DIR}/src>
diff --git a/src/StaticStack.h b/src/StaticStack.h
new file mode 100644
index 00000000..64886604
--- /dev/null
+++ b/src/StaticStack.h
@@ -0,0 +1,38 @@
+#include <array>
+#include <cstddef>
+
+template <typename T, size_t N> class StaticStack {
+public:
+ T Pop();
+ void Push(T element);
+ void Reset();
+ T Top();
+
+private:
+ std::array<T, N> elementArray;
+ // Number of elements in stack, points to the next empty slot
+ size_t stackPointer = 0;
+};
+
+// Returns random data when popping from empty array.
+template <typename T, size_t N> T StaticStack<T, N>::Pop() {
+ if (stackPointer > 0) {
+ stackPointer--;
+ }
+ return elementArray[stackPointer];
+}
+
+template <typename T, size_t N> void StaticStack<T, N>::Push(T element) {
+ if (stackPointer < elementArray.size()) {
+ elementArray[stackPointer] = element;
+ stackPointer++;
+ }
+}
+
+template <typename T, size_t N> void StaticStack<T, N>::Reset() {
+ stackPointer = 0;
+}
+
+template <typename T, size_t N> T StaticStack<T, N>::Top() {
+ return elementArray[stackPointer - 1];
+}
diff --git a/src/components/alarm/AlarmController.cpp b/src/components/alarm/AlarmController.cpp
index d97e1cff..88f65d9a 100644
--- a/src/components/alarm/AlarmController.cpp
+++ b/src/components/alarm/AlarmController.cpp
@@ -28,7 +28,7 @@ AlarmController::AlarmController(Controllers::DateTime& dateTimeController) : da
namespace {
void SetOffAlarm(TimerHandle_t xTimer) {
- auto controller = static_cast<Pinetime::Controllers::AlarmController*>(pvTimerGetTimerID(xTimer));
+ auto* controller = static_cast<Pinetime::Controllers::AlarmController*>(pvTimerGetTimerID(xTimer));
controller->SetOffAlarmNow();
}
}
diff --git a/src/components/alarm/AlarmController.h b/src/components/alarm/AlarmController.h
index 91f60f5a..8ac0de9a 100644
--- a/src/components/alarm/AlarmController.h
+++ b/src/components/alarm/AlarmController.h
@@ -26,6 +26,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class AlarmController {
public:
@@ -40,18 +41,23 @@ namespace Pinetime {
void StopAlerting();
enum class AlarmState { Not_Set, Set, Alerting };
enum class RecurType { None, Daily, Weekdays };
+
uint8_t Hours() const {
return hours;
}
+
uint8_t Minutes() const {
return minutes;
}
+
AlarmState State() const {
return state;
}
+
RecurType Recurrence() const {
return recurrence;
}
+
void SetRecurrence(RecurType recurType) {
recurrence = recurType;
}
diff --git a/src/components/battery/BatteryController.cpp b/src/components/battery/BatteryController.cpp
index 300d0978..4d860490 100644
--- a/src/components/battery/BatteryController.cpp
+++ b/src/components/battery/BatteryController.cpp
@@ -1,4 +1,5 @@
#include "components/battery/BatteryController.h"
+#include "components/utility/LinearApproximation.h"
#include "drivers/PinMap.h"
#include <hal/nrf_gpio.h>
#include <nrfx_saadc.h>
@@ -15,8 +16,8 @@ Battery::Battery() {
}
void Battery::ReadPowerState() {
- isCharging = !nrf_gpio_pin_read(PinMap::Charging);
- isPowerPresent = !nrf_gpio_pin_read(PinMap::PowerPresent);
+ isCharging = (nrf_gpio_pin_read(PinMap::Charging) == 0);
+ isPowerPresent = (nrf_gpio_pin_read(PinMap::PowerPresent) == 0);
if (isPowerPresent && !isCharging) {
isFull = true;
@@ -60,8 +61,8 @@ void Battery::SaadcInit() {
}
void Battery::SaadcEventHandler(nrfx_saadc_evt_t const* p_event) {
- const uint16_t battery_max = 4180; // maximum voltage of battery ( max charging voltage is 4.21 )
- const uint16_t battery_min = 3200; // minimum voltage of battery before shutdown ( depends on the battery )
+ static const Utility::LinearApproximation<uint16_t, uint8_t, 6> approx {
+ {{{3500, 0}, {3616, 3}, {3723, 22}, {3776, 48}, {3979, 79}, {4180, 100}}}};
if (p_event->type == NRFX_SAADC_EVT_DONE) {
@@ -74,19 +75,26 @@ void Battery::SaadcEventHandler(nrfx_saadc_evt_t const* p_event) {
// p_event->data.done.p_buffer[0] = (adc_voltage / reference_voltage) * 1024
voltage = p_event->data.done.p_buffer[0] * (8 * 600) / 1024;
- uint8_t newPercent;
- if (isFull) {
- newPercent = 100;
- } else if (voltage < battery_min) {
- newPercent = 0;
- } else {
- newPercent = std::min((voltage - battery_min) * 100 / (battery_max - battery_min), isCharging ? 99 : 100);
+ uint8_t newPercent = 100;
+ if (!isFull) {
+ // max. voltage while charging is higher than when discharging
+ newPercent = std::min(approx.GetValue(voltage), isCharging ? uint8_t {99} : uint8_t {100});
+ }
+
+ if (isPowerPresent) {
+ batteryLowNotified = false;
}
if ((isPowerPresent && newPercent > percentRemaining) || (!isPowerPresent && newPercent < percentRemaining) || firstMeasurement) {
firstMeasurement = false;
percentRemaining = newPercent;
systemTask->PushMessage(System::Messages::BatteryPercentageUpdated);
+
+ // warn about low battery when not charging and below threshold
+ if (BatteryIsLow() && !isPowerPresent && !batteryLowNotified) {
+ systemTask->PushMessage(System::Messages::LowBattery);
+ batteryLowNotified = true;
+ }
}
nrfx_saadc_uninit();
diff --git a/src/components/battery/BatteryController.h b/src/components/battery/BatteryController.h
index 5a7394c4..b47b77cc 100644
--- a/src/components/battery/BatteryController.h
+++ b/src/components/battery/BatteryController.h
@@ -18,6 +18,10 @@ namespace Pinetime {
return percentRemaining;
}
+ bool BatteryIsLow() const {
+ return percentRemaining <= lowBatteryThreshold;
+ }
+
uint16_t Voltage() const {
return voltage;
}
@@ -39,6 +43,7 @@ namespace Pinetime {
static constexpr nrf_saadc_input_t batteryVoltageAdcInput = NRF_SAADC_INPUT_AIN7;
uint16_t voltage = 0;
uint8_t percentRemaining = 0;
+ bool batteryLowNotified = false;
bool isFull = false;
bool isCharging = false;
@@ -50,6 +55,8 @@ namespace Pinetime {
void SaadcEventHandler(nrfx_saadc_evt_t const* p_event);
static void AdcCallbackStatic(nrfx_saadc_evt_t const* event);
+ static constexpr uint8_t lowBatteryThreshold {15};
+
bool isReading = false;
Pinetime::System::SystemTask* systemTask = nullptr;
diff --git a/src/components/ble/AlertNotificationClient.cpp b/src/components/ble/AlertNotificationClient.cpp
index 095fdef6..e3bc9242 100644
--- a/src/components/ble/AlertNotificationClient.cpp
+++ b/src/components/ble/AlertNotificationClient.cpp
@@ -35,9 +35,9 @@ namespace {
return client->OnDescriptorDiscoveryEventCallback(conn_handle, error, chr_val_handle, dsc);
}
- int NewAlertSubcribeCallback(uint16_t conn_handle, const struct ble_gatt_error* error, struct ble_gatt_attr* attr, void* arg) {
+ int NewAlertSubcribeCallback(uint16_t conn_handle, const struct ble_gatt_error* error, struct ble_gatt_attr* /*attr*/, void* arg) {
auto client = static_cast<AlertNotificationClient*>(arg);
- return client->OnNewAlertSubcribe(conn_handle, error, attr);
+ return client->OnNewAlertSubcribe(conn_handle, error);
}
}
@@ -107,7 +107,7 @@ int AlertNotificationClient::OnCharacteristicsDiscoveryEvent(uint16_t connection
return 0;
}
-int AlertNotificationClient::OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error* error, ble_gatt_attr* attribute) {
+int AlertNotificationClient::OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error* error) {
if (error->status == 0) {
NRF_LOG_INFO("ANS New alert subscribe OK");
} else {
diff --git a/src/components/ble/AlertNotificationClient.h b/src/components/ble/AlertNotificationClient.h
index 2d6a3873..b038f0d8 100644
--- a/src/components/ble/AlertNotificationClient.h
+++ b/src/components/ble/AlertNotificationClient.h
@@ -25,7 +25,7 @@ namespace Pinetime {
bool OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_svc* service);
int OnCharacteristicsDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_chr* characteristic);
- int OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error* error, ble_gatt_attr* attribute);
+ int OnNewAlertSubcribe(uint16_t connectionHandle, const ble_gatt_error* error);
int OnDescriptorDiscoveryEventCallback(uint16_t connectionHandle,
const ble_gatt_error* error,
uint16_t characteristicValueHandle,
diff --git a/src/components/ble/AlertNotificationService.cpp b/src/components/ble/AlertNotificationService.cpp
index 04819122..d9f28698 100644
--- a/src/components/ble/AlertNotificationService.cpp
+++ b/src/components/ble/AlertNotificationService.cpp
@@ -11,9 +11,9 @@ constexpr ble_uuid16_t AlertNotificationService::ansUuid;
constexpr ble_uuid16_t AlertNotificationService::ansCharUuid;
constexpr ble_uuid128_t AlertNotificationService::notificationEventUuid;
-int AlertNotificationCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+int AlertNotificationCallback(uint16_t /*conn_handle*/, uint16_t /*attr_handle*/, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto anService = static_cast<AlertNotificationService*>(arg);
- return anService->OnAlert(conn_handle, attr_handle, ctxt);
+ return anService->OnAlert(ctxt);
}
void AlertNotificationService::Init() {
@@ -44,7 +44,7 @@ AlertNotificationService::AlertNotificationService(System::SystemTask& systemTas
notificationManager {notificationManager} {
}
-int AlertNotificationService::OnAlert(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
+int AlertNotificationService::OnAlert(struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
constexpr size_t stringTerminatorSize = 1; // end of string '\0'
constexpr size_t headerSize = 3;
diff --git a/src/components/ble/AlertNotificationService.h b/src/components/ble/AlertNotificationService.h
index 5c7d428c..4b3c6385 100644
--- a/src/components/ble/AlertNotificationService.h
+++ b/src/components/ble/AlertNotificationService.h
@@ -16,6 +16,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class NotificationManager;
@@ -24,7 +25,7 @@ namespace Pinetime {
AlertNotificationService(Pinetime::System::SystemTask& systemTask, Pinetime::Controllers::NotificationManager& notificationManager);
void Init();
- int OnAlert(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
+ int OnAlert(struct ble_gatt_access_ctxt* ctxt);
void AcceptIncomingCall();
void RejectIncomingCall();
diff --git a/src/components/ble/BatteryInformationService.cpp b/src/components/ble/BatteryInformationService.cpp
index 9a3f86f5..db7c8566 100644
--- a/src/components/ble/BatteryInformationService.cpp
+++ b/src/components/ble/BatteryInformationService.cpp
@@ -7,9 +7,9 @@ using namespace Pinetime::Controllers;
constexpr ble_uuid16_t BatteryInformationService::batteryInformationServiceUuid;
constexpr ble_uuid16_t BatteryInformationService::batteryLevelUuid;
-int BatteryInformationServiceCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+int BatteryInformationServiceCallback(uint16_t /*conn_handle*/, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto* batteryInformationService = static_cast<BatteryInformationService*>(arg);
- return batteryInformationService->OnBatteryServiceRequested(conn_handle, attr_handle, ctxt);
+ return batteryInformationService->OnBatteryServiceRequested(attr_handle, ctxt);
}
BatteryInformationService::BatteryInformationService(Controllers::Battery& batteryController)
@@ -38,9 +38,7 @@ void BatteryInformationService::Init() {
ASSERT(res == 0);
}
-int BatteryInformationService::OnBatteryServiceRequested(uint16_t connectionHandle,
- uint16_t attributeHandle,
- ble_gatt_access_ctxt* context) {
+int BatteryInformationService::OnBatteryServiceRequested(uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
if (attributeHandle == batteryLevelHandle) {
NRF_LOG_INFO("BATTERY : handle = %d", batteryLevelHandle);
uint8_t batteryValue = batteryController.PercentRemaining();
@@ -49,6 +47,7 @@ int BatteryInformationService::OnBatteryServiceRequested(uint16_t connectionHand
}
return 0;
}
+
void BatteryInformationService::NotifyBatteryLevel(uint16_t connectionHandle, uint8_t level) {
auto* om = ble_hs_mbuf_from_flat(&level, 1);
ble_gattc_notify_custom(connectionHandle, batteryLevelHandle, om);
diff --git a/src/components/ble/BatteryInformationService.h b/src/components/ble/BatteryInformationService.h
index c6fc52e4..7f0a89ad 100644
--- a/src/components/ble/BatteryInformationService.h
+++ b/src/components/ble/BatteryInformationService.h
@@ -9,14 +9,16 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class Battery;
+
class BatteryInformationService {
public:
BatteryInformationService(Controllers::Battery& batteryController);
void Init();
- int OnBatteryServiceRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
+ int OnBatteryServiceRequested(uint16_t attributeHandle, ble_gatt_access_ctxt* context);
void NotifyBatteryLevel(uint16_t connectionHandle, uint8_t level);
private:
diff --git a/src/components/ble/BleController.h b/src/components/ble/BleController.h
index 675ede2d..de0a1bc2 100644
--- a/src/components/ble/BleController.h
+++ b/src/components/ble/BleController.h
@@ -24,6 +24,7 @@ namespace Pinetime {
void StopFirmwareUpdate();
void FirmwareUpdateTotalBytes(uint32_t totalBytes);
void FirmwareUpdateCurrentBytes(uint32_t currentBytes);
+
void State(FirmwareUpdateStates state) {
firmwareUpdateState = state;
}
@@ -31,12 +32,15 @@ namespace Pinetime {
bool IsFirmwareUpdating() const {
return isFirmwareUpdating;
}
+
uint32_t FirmwareUpdateTotalBytes() const {
return firmwareUpdateTotalBytes;
}
+
uint32_t FirmwareUpdateCurrentBytes() const {
return firmwareUpdateCurrentBytes;
}
+
FirmwareUpdateStates State() const {
return firmwareUpdateState;
}
@@ -44,15 +48,19 @@ namespace Pinetime {
void Address(BleAddress&& addr) {
address = addr;
}
+
const BleAddress& Address() const {
return address;
}
+
void AddressType(AddressTypes t) {
addressType = t;
}
+
void SetPairingKey(uint32_t k) {
pairingKey = k;
}
+
uint32_t GetPairingKey() const {
return pairingKey;
}
diff --git a/src/components/ble/CurrentTimeClient.cpp b/src/components/ble/CurrentTimeClient.cpp
index 53e98cb6..e535ae83 100644
--- a/src/components/ble/CurrentTimeClient.cpp
+++ b/src/components/ble/CurrentTimeClient.cpp
@@ -85,21 +85,11 @@ int CurrentTimeClient::OnCurrentTimeReadResult(uint16_t conn_handle, const ble_g
// TODO check that attribute->handle equals the handle discovered in OnCharacteristicDiscoveryEvent
CtsData result;
os_mbuf_copydata(attribute->om, 0, sizeof(CtsData), &result);
- NRF_LOG_INFO("Received data: %d-%d-%d %d:%d:%d",
- result.year,
- result.month,
- result.dayofmonth,
- result.hour,
- result.minute,
- result.second);
- dateTimeController.SetTime(result.year,
- result.month,
- result.dayofmonth,
- 0,
- result.hour,
- result.minute,
- result.second,
- nrf_rtc_counter_get(portNRF_RTC_REG));
+ uint16_t year = ((uint16_t) result.year_MSO << 8) + result.year_LSO;
+
+ NRF_LOG_INFO("Received data: %d-%d-%d %d:%d:%d", year, result.month, result.dayofmonth, result.hour, result.minute, result.second);
+ dateTimeController
+ .SetTime(year, result.month, result.dayofmonth, result.hour, result.minute, result.second, nrf_rtc_counter_get(portNRF_RTC_REG));
} else {
NRF_LOG_INFO("Error retrieving current time: %d", error->status);
}
diff --git a/src/components/ble/CurrentTimeClient.h b/src/components/ble/CurrentTimeClient.h
index 9e48be79..0a3a8735 100644
--- a/src/components/ble/CurrentTimeClient.h
+++ b/src/components/ble/CurrentTimeClient.h
@@ -19,24 +19,29 @@ namespace Pinetime {
bool OnDiscoveryEvent(uint16_t connectionHandle, const ble_gatt_error* error, const ble_gatt_svc* service);
int OnCharacteristicDiscoveryEvent(uint16_t conn_handle, const ble_gatt_error* error, const ble_gatt_chr* characteristic);
int OnCurrentTimeReadResult(uint16_t conn_handle, const ble_gatt_error* error, const ble_gatt_attr* attribute);
+
static constexpr const ble_uuid16_t* Uuid() {
return &CurrentTimeClient::ctsServiceUuid;
}
+
static constexpr const ble_uuid16_t* CurrentTimeCharacteristicUuid() {
return &CurrentTimeClient::currentTimeCharacteristicUuid;
}
+
void Discover(uint16_t connectionHandle, std::function<void(uint16_t)> lambda) override;
private:
typedef struct __attribute__((packed)) {
- uint16_t year;
+ uint8_t year_LSO; // explicit byte ordering to be independent of machine order
+ uint8_t year_MSO; // BLE GATT is little endian
uint8_t month;
uint8_t dayofmonth;
uint8_t hour;
uint8_t minute;
uint8_t second;
- uint8_t millis;
- uint8_t reason;
+ uint8_t dayofweek;
+ uint8_t fractions256; // currently ignored
+ uint8_t reason; // currently ignored, not that any host would set it anyway
} CtsData;
static constexpr uint16_t ctsServiceId {0x1805};
@@ -55,4 +60,4 @@ namespace Pinetime {
std::function<void(uint16_t)> onServiceDiscovered;
};
}
-} \ No newline at end of file
+}
diff --git a/src/components/ble/CurrentTimeService.cpp b/src/components/ble/CurrentTimeService.cpp
index 8430d1bc..856bc63a 100644
--- a/src/components/ble/CurrentTimeService.cpp
+++ b/src/components/ble/CurrentTimeService.cpp
@@ -5,11 +5,23 @@
using namespace Pinetime::Controllers;
constexpr ble_uuid16_t CurrentTimeService::ctsUuid;
-constexpr ble_uuid16_t CurrentTimeService::ctChrUuid;
+constexpr ble_uuid16_t CurrentTimeService::ctsCtChrUuid;
+constexpr ble_uuid16_t CurrentTimeService::ctsLtChrUuid;
-int CTSCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+int CTSCallback(uint16_t /*conn_handle*/, uint16_t /*attr_handle*/, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto cts = static_cast<CurrentTimeService*>(arg);
- return cts->OnTimeAccessed(conn_handle, attr_handle, ctxt);
+
+ return cts->OnCurrentTimeServiceAccessed(ctxt);
+}
+
+int CurrentTimeService::OnCurrentTimeServiceAccessed(struct ble_gatt_access_ctxt* ctxt) {
+ switch (ble_uuid_u16(ctxt->chr->uuid)) {
+ case ctsCurrentTimeCharId:
+ return OnCurrentTimeAccessed(ctxt);
+ case ctsLocalTimeCharId:
+ return OnLocalTimeAccessed(ctxt);
+ }
+ return -1; // Unknown characteristic
}
void CurrentTimeService::Init() {
@@ -18,45 +30,69 @@ void CurrentTimeService::Init() {
ASSERT(res == 0);
res = ble_gatts_add_svcs(serviceDefinition);
+
ASSERT(res == 0);
}
-int CurrentTimeService::OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
+int CurrentTimeService::OnCurrentTimeAccessed(struct ble_gatt_access_ctxt* ctxt) {
NRF_LOG_INFO("Setting time...");
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
- CtsData result;
- os_mbuf_copydata(ctxt->om, 0, sizeof(CtsData), &result);
+ CtsCurrentTimeData result;
+ int res = os_mbuf_copydata(ctxt->om, 0, sizeof(CtsCurrentTimeData), &result);
+ if (res < 0) {
+ NRF_LOG_ERROR("Error reading BLE Data writing to CTS Current Time (too little data)")
+ return BLE_ATT_ERR_INVALID_ATTR_VALUE_LEN;
+ }
+
+ uint16_t year = ((uint16_t) result.year_MSO << 8) + result.year_LSO;
- NRF_LOG_INFO("Received data: %d-%d-%d %d:%d:%d",
- result.year,
- result.month,
- result.dayofmonth,
- result.hour,
- result.minute,
- result.second);
+ NRF_LOG_INFO("Received data: %d-%d-%d %d:%d:%d", year, result.month, result.dayofmonth, result.hour, result.minute, result.second);
- m_dateTimeController.SetTime(result.year,
- result.month,
- result.dayofmonth,
- 0,
- result.hour,
- result.minute,
- result.second,
- nrf_rtc_counter_get(portNRF_RTC_REG));
+ m_dateTimeController
+ .SetTime(year, result.month, result.dayofmonth, result.hour, result.minute, result.second, nrf_rtc_counter_get(portNRF_RTC_REG));
} else if (ctxt->op == BLE_GATT_ACCESS_OP_READ_CHR) {
- CtsData currentDateTime;
- currentDateTime.year = m_dateTimeController.Year();
+ CtsCurrentTimeData currentDateTime;
+ currentDateTime.year_LSO = m_dateTimeController.Year() & 0xff;
+ currentDateTime.year_MSO = (m_dateTimeController.Year() >> 8) & 0xff;
currentDateTime.month = static_cast<u_int8_t>(m_dateTimeController.Month());
currentDateTime.dayofmonth = m_dateTimeController.Day();
currentDateTime.hour = m_dateTimeController.Hours();
currentDateTime.minute = m_dateTimeController.Minutes();
currentDateTime.second = m_dateTimeController.Seconds();
- currentDateTime.millis = 0;
+ currentDateTime.fractions256 = 0;
- int res = os_mbuf_append(ctxt->om, &currentDateTime, sizeof(CtsData));
+ int res = os_mbuf_append(ctxt->om, &currentDateTime, sizeof(CtsCurrentTimeData));
+ return (res == 0) ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
+ }
+
+ return 0;
+}
+
+int CurrentTimeService::OnLocalTimeAccessed(struct ble_gatt_access_ctxt* ctxt) {
+ NRF_LOG_INFO("Setting timezone...");
+
+ if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
+ CtsLocalTimeData result;
+ int res = os_mbuf_copydata(ctxt->om, 0, sizeof(CtsLocalTimeData), &result);
+
+ if (res < 0) {
+ NRF_LOG_ERROR("Error reading BLE Data writing to CTS Local Time (too little data)")
+ return BLE_ATT_ERR_INVALID_ATTR_VALUE_LEN;
+ }
+
+ NRF_LOG_INFO("Received data: %d %d", result.timezone, result.dst);
+
+ m_dateTimeController.SetTimeZone(result.timezone, result.dst);
+
+ } else if (ctxt->op == BLE_GATT_ACCESS_OP_READ_CHR) {
+ CtsLocalTimeData currentTimezone;
+ currentTimezone.timezone = m_dateTimeController.TzOffset();
+ currentTimezone.dst = m_dateTimeController.DstOffset();
+
+ int res = os_mbuf_append(ctxt->om, &currentTimezone, sizeof(currentTimezone));
return (res == 0) ? 0 : BLE_ATT_ERR_INSUFFICIENT_RES;
}
@@ -64,12 +100,19 @@ int CurrentTimeService::OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handl
}
CurrentTimeService::CurrentTimeService(DateTime& dateTimeController)
- : characteristicDefinition {{.uuid = &ctChrUuid.u,
+ : characteristicDefinition {
+
+ {.uuid = &ctsLtChrUuid.u,
.access_cb = CTSCallback,
+ .arg = this,
+ .flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ},
+ {.uuid = &ctsCtChrUuid.u,
+ .access_cb = CTSCallback,
.arg = this,
.flags = BLE_GATT_CHR_F_WRITE | BLE_GATT_CHR_F_READ},
- {0}},
+
+ {0}},
serviceDefinition {
{/* Device Information Service */
.type = BLE_GATT_SVC_TYPE_PRIMARY,
diff --git a/src/components/ble/CurrentTimeService.h b/src/components/ble/CurrentTimeService.h
index ca87d970..bec75a2b 100644
--- a/src/components/ble/CurrentTimeService.h
+++ b/src/components/ble/CurrentTimeService.h
@@ -16,29 +16,40 @@ namespace Pinetime {
CurrentTimeService(DateTime& dateTimeController);
void Init();
- int OnTimeAccessed(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
+ int OnCurrentTimeServiceAccessed(struct ble_gatt_access_ctxt* ctxt);
+ int OnCurrentTimeAccessed(struct ble_gatt_access_ctxt* ctxt);
+ int OnLocalTimeAccessed(struct ble_gatt_access_ctxt* ctxt);
private:
static constexpr uint16_t ctsId {0x1805};
- static constexpr uint16_t ctsCharId {0x2a2b};
+ static constexpr uint16_t ctsCurrentTimeCharId {0x2a2b};
+ static constexpr uint16_t ctsLocalTimeCharId {0x2a0f};
static constexpr ble_uuid16_t ctsUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsId};
- static constexpr ble_uuid16_t ctChrUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsCharId};
+ static constexpr ble_uuid16_t ctsCtChrUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsCurrentTimeCharId};
+ static constexpr ble_uuid16_t ctsLtChrUuid {.u {.type = BLE_UUID_TYPE_16}, .value = ctsLocalTimeCharId};
- struct ble_gatt_chr_def characteristicDefinition[2];
+ struct ble_gatt_chr_def characteristicDefinition[3];
struct ble_gatt_svc_def serviceDefinition[2];
typedef struct __attribute__((packed)) {
- uint16_t year;
+ uint8_t year_LSO; // BLE GATT is little endian
+ uint8_t year_MSO;
uint8_t month;
uint8_t dayofmonth;
uint8_t hour;
uint8_t minute;
uint8_t second;
- uint8_t millis;
- uint8_t reason;
- } CtsData;
+ uint8_t dayofweek;
+ uint8_t fractions256; // currently ignored
+ uint8_t reason; // currently ignored, not that any host would set it anyway
+ } CtsCurrentTimeData;
+
+ typedef struct __attribute__((packed)) {
+ int8_t timezone;
+ int8_t dst;
+ } CtsLocalTimeData;
DateTime& m_dateTimeController;
};
diff --git a/src/components/ble/DeviceInformationService.cpp b/src/components/ble/DeviceInformationService.cpp
index 0f47c90f..f0d1b5a7 100644
--- a/src/components/ble/DeviceInformationService.cpp
+++ b/src/components/ble/DeviceInformationService.cpp
@@ -10,9 +10,9 @@ constexpr ble_uuid16_t DeviceInformationService::deviceInfoUuid;
constexpr ble_uuid16_t DeviceInformationService::hwRevisionUuid;
constexpr ble_uuid16_t DeviceInformationService::swRevisionUuid;
-int DeviceInformationCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+int DeviceInformationCallback(uint16_t /*conn_handle*/, uint16_t /*attr_handle*/, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto deviceInformationService = static_cast<DeviceInformationService*>(arg);
- return deviceInformationService->OnDeviceInfoRequested(conn_handle, attr_handle, ctxt);
+ return deviceInformationService->OnDeviceInfoRequested(ctxt);
}
void DeviceInformationService::Init() {
@@ -24,7 +24,7 @@ void DeviceInformationService::Init() {
ASSERT(res == 0);
}
-int DeviceInformationService::OnDeviceInfoRequested(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
+int DeviceInformationService::OnDeviceInfoRequested(struct ble_gatt_access_ctxt* ctxt) {
const char* str;
switch (ble_uuid_u16(ctxt->chr->uuid)) {
diff --git a/src/components/ble/DeviceInformationService.h b/src/components/ble/DeviceInformationService.h
index a269afb4..c4babd1b 100644
--- a/src/components/ble/DeviceInformationService.h
+++ b/src/components/ble/DeviceInformationService.h
@@ -14,7 +14,7 @@ namespace Pinetime {
DeviceInformationService();
void Init();
- int OnDeviceInfoRequested(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
+ int OnDeviceInfoRequested(struct ble_gatt_access_ctxt* ctxt);
private:
static constexpr uint16_t deviceInfoId {0x180a};
@@ -50,4 +50,4 @@ namespace Pinetime {
struct ble_gatt_svc_def serviceDefinition[2];
};
}
-} \ No newline at end of file
+}
diff --git a/src/components/ble/DfuService.h b/src/components/ble/DfuService.h
index 4708a4a6..b56911b9 100644
--- a/src/components/ble/DfuService.h
+++ b/src/components/ble/DfuService.h
@@ -13,9 +13,11 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Drivers {
class SpiNorFlash;
}
+
namespace Controllers {
class Ble;
@@ -46,10 +48,12 @@ namespace Pinetime {
void OnNotificationTimer();
void Reset();
};
+
class DfuImage {
public:
DfuImage(Pinetime::Drivers::SpiNorFlash& spiNorFlash) : spiNorFlash {spiNorFlash} {
}
+
void Init(size_t chunkSize, size_t totalSize, uint16_t expectedCrc);
void Erase();
void Append(uint8_t* data, size_t size);
diff --git a/src/components/ble/FSService.h b/src/components/ble/FSService.h
index 828925a8..b2299623 100644
--- a/src/components/ble/FSService.h
+++ b/src/components/ble/FSService.h
@@ -11,8 +11,10 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class Ble;
+
class FSService {
public:
FSService(Pinetime::System::SystemTask& systemTask, Pinetime::Controllers::FS& fs);
@@ -71,6 +73,7 @@ namespace Pinetime {
FSState state;
char filepath[maxpathlen]; // TODO ..ugh fixed filepath len
int fileSize;
+
using ReadHeader = struct __attribute__((packed)) {
commands command;
uint8_t padding;
@@ -89,6 +92,7 @@ namespace Pinetime {
uint32_t chunklen;
uint8_t chunk[];
};
+
using ReadPacing = struct __attribute__((packed)) {
commands command;
uint8_t status;
@@ -124,6 +128,7 @@ namespace Pinetime {
uint32_t dataSize;
uint8_t data[];
};
+
using ListDirHeader = struct __attribute__((packed)) {
commands command;
uint8_t padding;
@@ -171,6 +176,7 @@ namespace Pinetime {
commands command;
uint8_t status;
};
+
using MoveHeader = struct __attribute__((packed)) {
commands command;
uint8_t padding;
diff --git a/src/components/ble/HeartRateService.cpp b/src/components/ble/HeartRateService.cpp
index d49a02c8..c522e67e 100644
--- a/src/components/ble/HeartRateService.cpp
+++ b/src/components/ble/HeartRateService.cpp
@@ -9,9 +9,9 @@ constexpr ble_uuid16_t HeartRateService::heartRateServiceUuid;
constexpr ble_uuid16_t HeartRateService::heartRateMeasurementUuid;
namespace {
- int HeartRateServiceCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+ int HeartRateServiceCallback(uint16_t /*conn_handle*/, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto* heartRateService = static_cast<HeartRateService*>(arg);
- return heartRateService->OnHeartRateRequested(conn_handle, attr_handle, ctxt);
+ return heartRateService->OnHeartRateRequested(attr_handle, ctxt);
}
}
@@ -45,7 +45,7 @@ void HeartRateService::Init() {
ASSERT(res == 0);
}
-int HeartRateService::OnHeartRateRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
+int HeartRateService::OnHeartRateRequested(uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
if (attributeHandle == heartRateMeasurementHandle) {
NRF_LOG_INFO("HEARTRATE : handle = %d", heartRateMeasurementHandle);
uint8_t buffer[2] = {0, heartRateController.HeartRate()}; // [0] = flags, [1] = hr value
@@ -60,7 +60,7 @@ void HeartRateService::OnNewHeartRateValue(uint8_t heartRateValue) {
if (!heartRateMeasurementNotificationEnable)
return;
- uint8_t buffer[2] = {0, heartRateController.HeartRate()}; // [0] = flags, [1] = hr value
+ uint8_t buffer[2] = {0, heartRateValue}; // [0] = flags, [1] = hr value
auto* om = ble_hs_mbuf_from_flat(buffer, 2);
uint16_t connectionHandle = system.nimble().connHandle();
@@ -72,12 +72,12 @@ void HeartRateService::OnNewHeartRateValue(uint8_t heartRateValue) {
ble_gattc_notify_custom(connectionHandle, heartRateMeasurementHandle, om);
}
-void HeartRateService::SubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle) {
+void HeartRateService::SubscribeNotification(uint16_t attributeHandle) {
if (attributeHandle == heartRateMeasurementHandle)
heartRateMeasurementNotificationEnable = true;
}
-void HeartRateService::UnsubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle) {
+void HeartRateService::UnsubscribeNotification(uint16_t attributeHandle) {
if (attributeHandle == heartRateMeasurementHandle)
heartRateMeasurementNotificationEnable = false;
-} \ No newline at end of file
+}
diff --git a/src/components/ble/HeartRateService.h b/src/components/ble/HeartRateService.h
index 4e4a5a42..003bdbd1 100644
--- a/src/components/ble/HeartRateService.h
+++ b/src/components/ble/HeartRateService.h
@@ -10,17 +10,19 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class HeartRateController;
+
class HeartRateService {
public:
HeartRateService(Pinetime::System::SystemTask& system, Controllers::HeartRateController& heartRateController);
void Init();
- int OnHeartRateRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
+ int OnHeartRateRequested(uint16_t attributeHandle, ble_gatt_access_ctxt* context);
void OnNewHeartRateValue(uint8_t hearRateValue);
- void SubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle);
- void UnsubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle);
+ void SubscribeNotification(uint16_t attributeHandle);
+ void UnsubscribeNotification(uint16_t attributeHandle);
private:
Pinetime::System::SystemTask& system;
diff --git a/src/components/ble/ImmediateAlertService.cpp b/src/components/ble/ImmediateAlertService.cpp
index c80b3783..b9de615a 100644
--- a/src/components/ble/ImmediateAlertService.cpp
+++ b/src/components/ble/ImmediateAlertService.cpp
@@ -9,9 +9,9 @@ constexpr ble_uuid16_t ImmediateAlertService::immediateAlertServiceUuid;
constexpr ble_uuid16_t ImmediateAlertService::alertLevelUuid;
namespace {
- int AlertLevelCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+ int AlertLevelCallback(uint16_t /*conn_handle*/, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto* immediateAlertService = static_cast<ImmediateAlertService*>(arg);
- return immediateAlertService->OnAlertLevelChanged(conn_handle, attr_handle, ctxt);
+ return immediateAlertService->OnAlertLevelChanged(attr_handle, ctxt);
}
const char* ToString(ImmediateAlertService::Levels level) {
@@ -56,7 +56,7 @@ void ImmediateAlertService::Init() {
ASSERT(res == 0);
}
-int ImmediateAlertService::OnAlertLevelChanged(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
+int ImmediateAlertService::OnAlertLevelChanged(uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
if (attributeHandle == alertLevelHandle) {
if (context->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
auto alertLevel = static_cast<Levels>(context->om->om_data[0]);
diff --git a/src/components/ble/ImmediateAlertService.h b/src/components/ble/ImmediateAlertService.h
index 1f778acd..47a05439 100644
--- a/src/components/ble/ImmediateAlertService.h
+++ b/src/components/ble/ImmediateAlertService.h
@@ -9,15 +9,17 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class NotificationManager;
+
class ImmediateAlertService {
public:
enum class Levels : uint8_t { NoAlert = 0, MildAlert = 1, HighAlert = 2 };
ImmediateAlertService(Pinetime::System::SystemTask& systemTask, Pinetime::Controllers::NotificationManager& notificationManager);
void Init();
- int OnAlertLevelChanged(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
+ int OnAlertLevelChanged(uint16_t attributeHandle, ble_gatt_access_ctxt* context);
private:
Pinetime::System::SystemTask& systemTask;
diff --git a/src/components/ble/MotionService.cpp b/src/components/ble/MotionService.cpp
index 121ad3b0..604f22d5 100644
--- a/src/components/ble/MotionService.cpp
+++ b/src/components/ble/MotionService.cpp
@@ -21,9 +21,9 @@ namespace {
constexpr ble_uuid128_t stepCountCharUuid {CharUuid(0x01, 0x00)};
constexpr ble_uuid128_t motionValuesCharUuid {CharUuid(0x02, 0x00)};
- int MotionServiceCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+ int MotionServiceCallback(uint16_t /*conn_handle*/, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
auto* motionService = static_cast<MotionService*>(arg);
- return motionService->OnStepCountRequested(conn_handle, attr_handle, ctxt);
+ return motionService->OnStepCountRequested(attr_handle, ctxt);
}
}
@@ -59,7 +59,7 @@ void MotionService::Init() {
ASSERT(res == 0);
}
-int MotionService::OnStepCountRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
+int MotionService::OnStepCountRequested(uint16_t attributeHandle, ble_gatt_access_ctxt* context) {
if (attributeHandle == stepCountHandle) {
NRF_LOG_INFO("Motion-stepcount : handle = %d", stepCountHandle);
uint32_t buffer = motionController.NbSteps();
@@ -90,11 +90,12 @@ void MotionService::OnNewStepCountValue(uint32_t stepCount) {
ble_gattc_notify_custom(connectionHandle, stepCountHandle, om);
}
+
void MotionService::OnNewMotionValues(int16_t x, int16_t y, int16_t z) {
if (!motionValuesNoficationEnabled)
return;
- int16_t buffer[3] = {motionController.X(), motionController.Y(), motionController.Z()};
+ int16_t buffer[3] = {x, y, z};
auto* om = ble_hs_mbuf_from_flat(buffer, 3 * sizeof(int16_t));
uint16_t connectionHandle = system.nimble().connHandle();
@@ -106,14 +107,14 @@ void MotionService::OnNewMotionValues(int16_t x, int16_t y, int16_t z) {
ble_gattc_notify_custom(connectionHandle, motionValuesHandle, om);
}
-void MotionService::SubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle) {
+void MotionService::SubscribeNotification(uint16_t attributeHandle) {
if (attributeHandle == stepCountHandle)
stepCountNoficationEnabled = true;
else if (attributeHandle == motionValuesHandle)
motionValuesNoficationEnabled = true;
}
-void MotionService::UnsubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle) {
+void MotionService::UnsubscribeNotification(uint16_t attributeHandle) {
if (attributeHandle == stepCountHandle)
stepCountNoficationEnabled = false;
else if (attributeHandle == motionValuesHandle)
diff --git a/src/components/ble/MotionService.h b/src/components/ble/MotionService.h
index 1b4ac0a3..1b172528 100644
--- a/src/components/ble/MotionService.h
+++ b/src/components/ble/MotionService.h
@@ -10,18 +10,20 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class MotionController;
+
class MotionService {
public:
MotionService(Pinetime::System::SystemTask& system, Controllers::MotionController& motionController);
void Init();
- int OnStepCountRequested(uint16_t connectionHandle, uint16_t attributeHandle, ble_gatt_access_ctxt* context);
+ int OnStepCountRequested(uint16_t attributeHandle, ble_gatt_access_ctxt* context);
void OnNewStepCountValue(uint32_t stepCount);
void OnNewMotionValues(int16_t x, int16_t y, int16_t z);
- void SubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle);
- void UnsubscribeNotification(uint16_t connectionHandle, uint16_t attributeHandle);
+ void SubscribeNotification(uint16_t attributeHandle);
+ void UnsubscribeNotification(uint16_t attributeHandle);
private:
Pinetime::System::SystemTask& system;
diff --git a/src/components/ble/MusicService.cpp b/src/components/ble/MusicService.cpp
index fc7cef01..403c957b 100644
--- a/src/components/ble/MusicService.cpp
+++ b/src/components/ble/MusicService.cpp
@@ -48,8 +48,8 @@ namespace {
constexpr uint8_t MaxStringSize {40};
- int MusicCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
- return static_cast<Pinetime::Controllers::MusicService*>(arg)->OnCommand(conn_handle, attr_handle, ctxt);
+ int MusicCallback(uint16_t /*conn_handle*/, uint16_t /*attr_handle*/, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+ return static_cast<Pinetime::Controllers::MusicService*>(arg)->OnCommand(ctxt);
}
}
@@ -122,7 +122,7 @@ void Pinetime::Controllers::MusicService::Init() {
ASSERT(res == 0);
}
-int Pinetime::Controllers::MusicService::OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
+int Pinetime::Controllers::MusicService::OnCommand(struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
size_t notifSize = OS_MBUF_PKTLEN(ctxt->om);
size_t bufferSize = notifSize;
diff --git a/src/components/ble/MusicService.h b/src/components/ble/MusicService.h
index 047d0d26..6aebc3c5 100644
--- a/src/components/ble/MusicService.h
+++ b/src/components/ble/MusicService.h
@@ -30,6 +30,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class MusicService {
public:
@@ -37,7 +38,7 @@ namespace Pinetime {
void Init();
- int OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
+ int OnCommand(struct ble_gatt_access_ctxt* ctxt);
void event(char event);
diff --git a/src/components/ble/NavigationService.cpp b/src/components/ble/NavigationService.cpp
index 76143686..5508d08c 100644
--- a/src/components/ble/NavigationService.cpp
+++ b/src/components/ble/NavigationService.cpp
@@ -39,9 +39,9 @@ namespace {
constexpr ble_uuid128_t navManDistCharUuid {CharUuid(0x03, 0x00)};
constexpr ble_uuid128_t navProgressCharUuid {CharUuid(0x04, 0x00)};
- int NAVCallback(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
- auto navService = static_cast<Pinetime::Controllers::NavigationService*>(arg);
- return navService->OnCommand(conn_handle, attr_handle, ctxt);
+ int NAVCallback(uint16_t /*conn_handle*/, uint16_t /*attr_handle*/, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+ auto* navService = static_cast<Pinetime::Controllers::NavigationService*>(arg);
+ return navService->OnCommand(ctxt);
}
} // namespace
@@ -81,7 +81,7 @@ void Pinetime::Controllers::NavigationService::Init() {
ASSERT(res == 0);
}
-int Pinetime::Controllers::NavigationService::OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt) {
+int Pinetime::Controllers::NavigationService::OnCommand(struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
size_t notifSize = OS_MBUF_PKTLEN(ctxt->om);
diff --git a/src/components/ble/NavigationService.h b/src/components/ble/NavigationService.h
index c0c77f35..1c1739ba 100644
--- a/src/components/ble/NavigationService.h
+++ b/src/components/ble/NavigationService.h
@@ -30,6 +30,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class NavigationService {
@@ -38,7 +39,7 @@ namespace Pinetime {
void Init();
- int OnCommand(uint16_t conn_handle, uint16_t attr_handle, struct ble_gatt_access_ctxt* ctxt);
+ int OnCommand(struct ble_gatt_access_ctxt* ctxt);
std::string getFlag();
diff --git a/src/components/ble/NimbleController.cpp b/src/components/ble/NimbleController.cpp
index 52f4e4ce..912f5927 100644
--- a/src/components/ble/NimbleController.cpp
+++ b/src/components/ble/NimbleController.cpp
@@ -322,14 +322,14 @@ int NimbleController::OnGAPEvent(ble_gap_event* event) {
event->subscribe.prev_indicate);
if (event->subscribe.reason == BLE_GAP_SUBSCRIBE_REASON_TERM) {
- heartRateService.UnsubscribeNotification(event->subscribe.conn_handle, event->subscribe.attr_handle);
- motionService.UnsubscribeNotification(event->subscribe.conn_handle, event->subscribe.attr_handle);
+ heartRateService.UnsubscribeNotification(event->subscribe.attr_handle);
+ motionService.UnsubscribeNotification(event->subscribe.attr_handle);
} else if (event->subscribe.prev_notify == 0 && event->subscribe.cur_notify == 1) {
- heartRateService.SubscribeNotification(event->subscribe.conn_handle, event->subscribe.attr_handle);
- motionService.SubscribeNotification(event->subscribe.conn_handle, event->subscribe.attr_handle);
+ heartRateService.SubscribeNotification(event->subscribe.attr_handle);
+ motionService.SubscribeNotification(event->subscribe.attr_handle);
} else if (event->subscribe.prev_notify == 1 && event->subscribe.cur_notify == 0) {
- heartRateService.UnsubscribeNotification(event->subscribe.conn_handle, event->subscribe.attr_handle);
- motionService.UnsubscribeNotification(event->subscribe.conn_handle, event->subscribe.attr_handle);
+ heartRateService.UnsubscribeNotification(event->subscribe.attr_handle);
+ motionService.UnsubscribeNotification(event->subscribe.attr_handle);
}
break;
diff --git a/src/components/ble/NimbleController.h b/src/components/ble/NimbleController.h
index 000231fe..8f1dfed7 100644
--- a/src/components/ble/NimbleController.h
+++ b/src/components/ble/NimbleController.h
@@ -58,12 +58,15 @@ namespace Pinetime {
Pinetime::Controllers::MusicService& music() {
return musicService;
};
+
Pinetime::Controllers::NavigationService& navigation() {
return navService;
};
+
Pinetime::Controllers::AlertNotificationService& alertService() {
return anService;
};
+
Pinetime::Controllers::WeatherService& weather() {
return weatherService;
};
diff --git a/src/components/ble/NotificationManager.h b/src/components/ble/NotificationManager.h
index 4c199dbf..09b5a561 100644
--- a/src/components/ble/NotificationManager.h
+++ b/src/components/ble/NotificationManager.h
@@ -51,9 +51,11 @@ namespace Pinetime {
static constexpr size_t MaximumMessageSize() {
return MessageSize;
};
+
bool IsEmpty() const {
return size == 0;
}
+
size_t NbNotifications() const;
private:
diff --git a/src/components/ble/weather/WeatherService.cpp b/src/components/ble/weather/WeatherService.cpp
index 23f53b74..e606d9bf 100644
--- a/src/components/ble/weather/WeatherService.cpp
+++ b/src/components/ble/weather/WeatherService.cpp
@@ -20,8 +20,8 @@
#include "libs/QCBOR/inc/qcbor/qcbor.h"
#include "systemtask/SystemTask.h"
-int WeatherCallback(uint16_t connHandle, uint16_t attrHandle, struct ble_gatt_access_ctxt* ctxt, void* arg) {
- return static_cast<Pinetime::Controllers::WeatherService*>(arg)->OnCommand(connHandle, attrHandle, ctxt);
+int WeatherCallback(uint16_t /*connHandle*/, uint16_t /*attrHandle*/, struct ble_gatt_access_ctxt* ctxt, void* arg) {
+ return static_cast<Pinetime::Controllers::WeatherService*>(arg)->OnCommand(ctxt);
}
namespace Pinetime {
@@ -41,7 +41,7 @@ namespace Pinetime {
ASSERT(res == 0);
}
- int WeatherService::OnCommand(uint16_t connHandle, uint16_t attrHandle, struct ble_gatt_access_ctxt* ctxt) {
+ int WeatherService::OnCommand(struct ble_gatt_access_ctxt* ctxt) {
if (ctxt->op == BLE_GATT_ACCESS_OP_WRITE_CHR) {
const uint8_t packetLen = OS_MBUF_PKTLEN(ctxt->om); // NOLINT(cppcoreguidelines-pro-bounds-pointer-arithmetic)
if (packetLen <= 0) {
@@ -552,11 +552,12 @@ namespace Pinetime {
int16_t WeatherService::GetTodayMinTemp() const {
uint64_t currentTimestamp = GetCurrentUnixTimestamp();
- uint64_t currentDayEnd = currentTimestamp - ((24 - dateTimeController.Hours()) * 60 * 60) -
- ((60 - dateTimeController.Minutes()) * 60) - (60 - dateTimeController.Seconds());
+ uint64_t currentDayEnd = currentTimestamp + ((24 - dateTimeController.Hours()) * 60 * 60) +
+ ((60 - dateTimeController.Minutes()) * 60) + (60 - dateTimeController.Seconds());
+ uint64_t currentDayStart = currentDayEnd - 86400;
int16_t result = -32768;
for (auto&& header : this->timeline) {
- if (header->eventType == WeatherData::eventtype::Temperature && IsEventStillValid(header, currentTimestamp) &&
+ if (header->eventType == WeatherData::eventtype::Temperature && header->timestamp >= currentDayStart &&
header->timestamp < currentDayEnd &&
reinterpret_cast<const std::unique_ptr<WeatherData::Temperature>&>(header)->temperature != -32768) {
int16_t temperature = reinterpret_cast<const std::unique_ptr<WeatherData::Temperature>&>(header)->temperature;
@@ -575,11 +576,12 @@ namespace Pinetime {
int16_t WeatherService::GetTodayMaxTemp() const {
uint64_t currentTimestamp = GetCurrentUnixTimestamp();
- uint64_t currentDayEnd = currentTimestamp - ((24 - dateTimeController.Hours()) * 60 * 60) -
- ((60 - dateTimeController.Minutes()) * 60) - (60 - dateTimeController.Seconds());
+ uint64_t currentDayEnd = currentTimestamp + ((24 - dateTimeController.Hours()) * 60 * 60) +
+ ((60 - dateTimeController.Minutes()) * 60) + (60 - dateTimeController.Seconds());
+ uint64_t currentDayStart = currentDayEnd - 86400;
int16_t result = -32768;
for (auto&& header : this->timeline) {
- if (header->eventType == WeatherData::eventtype::Temperature && IsEventStillValid(header, currentTimestamp) &&
+ if (header->eventType == WeatherData::eventtype::Temperature && header->timestamp >= currentDayStart &&
header->timestamp < currentDayEnd &&
reinterpret_cast<const std::unique_ptr<WeatherData::Temperature>&>(header)->temperature != -32768) {
int16_t temperature = reinterpret_cast<const std::unique_ptr<WeatherData::Temperature>&>(header)->temperature;
diff --git a/src/components/ble/weather/WeatherService.h b/src/components/ble/weather/WeatherService.h
index e37417da..00650e90 100644
--- a/src/components/ble/weather/WeatherService.h
+++ b/src/components/ble/weather/WeatherService.h
@@ -39,6 +39,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class WeatherService {
@@ -47,7 +48,7 @@ namespace Pinetime {
void Init();
- int OnCommand(uint16_t connHandle, uint16_t attrHandle, struct ble_gatt_access_ctxt* ctxt);
+ int OnCommand(struct ble_gatt_access_ctxt* ctxt);
/*
* Helper functions for quick access to currently valid data
diff --git a/src/components/datetime/DateTimeController.cpp b/src/components/datetime/DateTimeController.cpp
index 4dc16329..b744fbb2 100644
--- a/src/components/datetime/DateTimeController.cpp
+++ b/src/components/datetime/DateTimeController.cpp
@@ -20,14 +20,7 @@ void DateTime::SetCurrentTime(std::chrono::time_point<std::chrono::system_clock,
UpdateTime(previousSystickCounter); // Update internal state without updating the time
}
-void DateTime::SetTime(uint16_t year,
- uint8_t month,
- uint8_t day,
- uint8_t dayOfWeek,
- uint8_t hour,
- uint8_t minute,
- uint8_t second,
- uint32_t systickCounter) {
+void DateTime::SetTime(uint16_t year, uint8_t month, uint8_t day, uint8_t hour, uint8_t minute, uint8_t second, uint32_t systickCounter) {
std::tm tm = {
/* .tm_sec = */ second,
/* .tm_min = */ minute,
@@ -36,6 +29,7 @@ void DateTime::SetTime(uint16_t year,
/* .tm_mon = */ month - 1,
/* .tm_year = */ year - 1900,
};
+
tm.tm_isdst = -1; // Use DST value from local time zone
currentDateTime = std::chrono::system_clock::from_time_t(std::mktime(&tm));
@@ -50,6 +44,11 @@ void DateTime::SetTime(uint16_t year,
systemTask->PushMessage(System::Messages::OnNewTime);
}
+void DateTime::SetTimeZone(int8_t timezone, int8_t dst) {
+ tzOffset = timezone;
+ dstOffset = dst;
+}
+
void DateTime::UpdateTime(uint32_t systickCounter) {
// Handle systick counter overflow
uint32_t systickDelta = 0;
@@ -136,6 +135,7 @@ void DateTime::Register(Pinetime::System::SystemTask* systemTask) {
}
using ClockType = Pinetime::Controllers::Settings::ClockType;
+
std::string DateTime::FormattedTime() {
// Return time as a string in 12- or 24-hour format
char buff[9];
diff --git a/src/components/datetime/DateTimeController.h b/src/components/datetime/DateTimeController.h
index 81319d15..74ccf4da 100644
--- a/src/components/datetime/DateTimeController.h
+++ b/src/components/datetime/DateTimeController.h
@@ -9,6 +9,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class DateTime {
public:
@@ -30,37 +31,85 @@ namespace Pinetime {
December
};
- void SetTime(uint16_t year,
- uint8_t month,
- uint8_t day,
- uint8_t dayOfWeek,
- uint8_t hour,
- uint8_t minute,
- uint8_t second,
- uint32_t systickCounter);
+ void SetTime(uint16_t year, uint8_t month, uint8_t day, uint8_t hour, uint8_t minute, uint8_t second, uint32_t systickCounter);
+
+ /*
+ * setter corresponding to the BLE Set Local Time characteristic.
+ *
+ * used to update difference between utc and local time (see UtcOffset())
+ *
+ * parameters are in quarters of an our. Following the BLE CTS specification,
+ * timezone is expected to be constant over DST which will be reported in
+ * dst field.
+ */
+ void SetTimeZone(int8_t timezone, int8_t dst);
+
void UpdateTime(uint32_t systickCounter);
+
uint16_t Year() const {
return year;
}
+
Months Month() const {
return month;
}
+
uint8_t Day() const {
return day;
}
+
Days DayOfWeek() const {
return dayOfWeek;
}
+
uint8_t Hours() const {
return hour;
}
+
uint8_t Minutes() const {
return minute;
}
+
uint8_t Seconds() const {
return second;
}
+ /*
+ * returns the offset between local time and UTC in quarters of an hour
+ *
+ * Availability of this field depends on wether the companion app
+ * supports the BLE CTS Local Time Characteristic. Expect it to be 0
+ * if not.
+ */
+ int8_t UtcOffset() const {
+ return tzOffset + dstOffset;
+ }
+
+ /*
+ * returns the offset between the (dst independent) local time zone and UTC
+ * in quarters of an hour
+ *
+ * Availability of this field depends on wether the companion app
+ * supports the BLE CTS Local Time Characteristic. Expect it to be 0
+ * if not.
+ */
+ int8_t TzOffset() const {
+ return tzOffset;
+ }
+
+ /*
+ * returns the offset between the local time zone and local time
+ * in quarters of an hour
+ * if != 0, DST is in effect, if == 0 not.
+ *
+ * Availability of this field depends on wether the companion app
+ * supports the BLE CTS Local Time Characteristic. Expect it to be 0
+ * if not.
+ */
+ int8_t DstOffset() const {
+ return dstOffset;
+ }
+
const char* MonthShortToString() const;
const char* DayOfWeekShortToString() const;
static const char* MonthShortToStringLow(Months month);
@@ -69,6 +118,11 @@ namespace Pinetime {
std::chrono::time_point<std::chrono::system_clock, std::chrono::nanoseconds> CurrentDateTime() const {
return currentDateTime;
}
+
+ std::chrono::time_point<std::chrono::system_clock, std::chrono::nanoseconds> UTCDateTime() const {
+ return currentDateTime - std::chrono::seconds((tzOffset + dstOffset) * 15 * 60);
+ }
+
std::chrono::seconds Uptime() const {
return uptime;
}
@@ -85,6 +139,8 @@ namespace Pinetime {
uint8_t hour = 0;
uint8_t minute = 0;
uint8_t second = 0;
+ int8_t tzOffset = 0;
+ int8_t dstOffset = 0;
uint32_t previousSystickCounter = 0;
std::chrono::time_point<std::chrono::system_clock, std::chrono::nanoseconds> currentDateTime;
diff --git a/src/components/fs/FS.cpp b/src/components/fs/FS.cpp
index 14b05525..0bb59afa 100644
--- a/src/components/fs/FS.cpp
+++ b/src/components/fs/FS.cpp
@@ -89,18 +89,23 @@ int FS::DirClose(lfs_dir_t* lfs_dir) {
int FS::DirRead(lfs_dir_t* dir, lfs_info* info) {
return lfs_dir_read(&lfs, dir, info);
}
+
int FS::DirRewind(lfs_dir_t* dir) {
return lfs_dir_rewind(&lfs, dir);
}
+
int FS::DirCreate(const char* path) {
return lfs_mkdir(&lfs, path);
}
+
int FS::Rename(const char* oldPath, const char* newPath) {
return lfs_rename(&lfs, oldPath, newPath);
}
+
int FS::Stat(const char* path, lfs_info* info) {
return lfs_stat(&lfs, path, info);
}
+
lfs_ssize_t FS::GetFSSize() {
return lfs_fs_size(&lfs);
}
@@ -110,7 +115,7 @@ lfs_ssize_t FS::GetFSSize() {
----------- Interface between littlefs and SpiNorFlash -----------
*/
-int FS::SectorSync(const struct lfs_config* c) {
+int FS::SectorSync(const struct lfs_config* /*c*/) {
return 0;
}
@@ -142,7 +147,7 @@ int FS::SectorRead(const struct lfs_config* c, lfs_block_t block, lfs_off_t off,
*/
namespace {
- lv_fs_res_t lvglOpen(lv_fs_drv_t* drv, void* file_p, const char* path, lv_fs_mode_t mode) {
+ lv_fs_res_t lvglOpen(lv_fs_drv_t* drv, void* file_p, const char* path, lv_fs_mode_t /*mode*/) {
lfs_file_t* file = static_cast<lfs_file_t*>(file_p);
FS* filesys = static_cast<FS*>(drv->user_data);
int res = filesys->FileOpen(file, path, LFS_O_RDONLY);
@@ -195,4 +200,4 @@ void FS::LVGLFileSystemInit() {
fs_drv.user_data = this;
lv_fs_drv_register(&fs_drv);
-} \ No newline at end of file
+}
diff --git a/src/components/fs/FS.h b/src/components/fs/FS.h
index 87fcdc23..9730e474 100644
--- a/src/components/fs/FS.h
+++ b/src/components/fs/FS.h
@@ -35,6 +35,7 @@ namespace Pinetime {
static size_t getSize() {
return size;
}
+
static size_t getBlockSize() {
return blockSize;
}
diff --git a/src/components/gfx/Gfx.h b/src/components/gfx/Gfx.h
index 54c4a8b7..17c248f7 100644
--- a/src/components/gfx/Gfx.h
+++ b/src/components/gfx/Gfx.h
@@ -10,6 +10,7 @@ namespace Pinetime {
namespace Drivers {
class St7789;
}
+
namespace Components {
class Gfx : public Pinetime::Drivers::BufferProvider {
public:
@@ -33,9 +34,11 @@ namespace Pinetime {
static constexpr uint8_t height = 240;
enum class Action { None, FillRectangle, DrawChar };
+
struct State {
State() : busy {false}, action {Action::None}, remainingIterations {0}, currentIteration {0} {
}
+
volatile bool busy;
volatile Action action;
volatile uint16_t remainingIterations;
diff --git a/src/components/heartrate/HeartRateController.h b/src/components/heartrate/HeartRateController.h
index a63f1a70..f66c79f8 100644
--- a/src/components/heartrate/HeartRateController.h
+++ b/src/components/heartrate/HeartRateController.h
@@ -7,9 +7,11 @@ namespace Pinetime {
namespace Applications {
class HeartRateTask;
}
+
namespace System {
class SystemTask;
}
+
namespace Controllers {
class HeartRateController {
public:
@@ -21,9 +23,11 @@ namespace Pinetime {
void Update(States newState, uint8_t heartRate);
void SetHeartRateTask(Applications::HeartRateTask* task);
+
States State() const {
return state;
}
+
uint8_t HeartRate() const {
return heartRate;
}
diff --git a/src/components/heartrate/Ppg.cpp b/src/components/heartrate/Ppg.cpp
index a5d83696..900b1c22 100644
--- a/src/components/heartrate/Ppg.cpp
+++ b/src/components/heartrate/Ppg.cpp
@@ -29,8 +29,9 @@ namespace {
auto z1 = CompareShift(d, mn - 1, size);
for (int i = mn; i < mx + 1; i++) {
auto z = CompareShift(d, i, size);
- if (z2 > z1 && z1 < z)
+ if (z2 > z1 && z1 < z) {
return i;
+ }
z2 = z1;
z1 = z;
}
@@ -52,41 +53,48 @@ int8_t Ppg::Preprocess(float spl) {
auto spl_int = static_cast<int8_t>(spl);
- if (dataIndex < 200)
+ if (dataIndex < 200) {
data[dataIndex++] = spl_int;
+ }
return spl_int;
}
-float Ppg::HeartRate() {
- if (dataIndex < 200)
+int Ppg::HeartRate() {
+ if (dataIndex < 200) {
return 0;
+ }
NRF_LOG_INFO("PREPROCESS, offset = %d", offset);
auto hr = ProcessHeartRate();
dataIndex = 0;
return hr;
}
-float Ppg::ProcessHeartRate() {
- auto t0 = Trough(data.data(), dataIndex, 7, 48);
- if (t0 < 0)
+
+int Ppg::ProcessHeartRate() {
+ int t0 = Trough(data.data(), dataIndex, 7, 48);
+ if (t0 < 0) {
return 0;
+ }
- float t1 = t0 * 2;
+ int t1 = t0 * 2;
t1 = Trough(data.data(), dataIndex, t1 - 5, t1 + 5);
- if (t1 < 0)
+ if (t1 < 0) {
return 0;
+ }
- float t2 = static_cast<int>(t1 * 3) / 2;
+ int t2 = (t1 * 3) / 2;
t2 = Trough(data.data(), dataIndex, t2 - 5, t2 + 5);
- if (t2 < 0)
+ if (t2 < 0) {
return 0;
+ }
- float t3 = static_cast<int>(t2 * 4) / 3;
+ int t3 = (t2 * 4) / 3;
t3 = Trough(data.data(), dataIndex, t3 - 4, t3 + 4);
- if (t3 < 0)
- return static_cast<int>(60 * 24 * 3) / static_cast<int>(t2);
+ if (t3 < 0) {
+ return (60 * 24 * 3) / t2;
+ }
- return static_cast<int>(60 * 24 * 4) / static_cast<int>(t3);
+ return (60 * 24 * 4) / t3;
}
void Ppg::SetOffset(uint16_t offset) {
diff --git a/src/components/heartrate/Ppg.h b/src/components/heartrate/Ppg.h
index 7000c871..1f709bab 100644
--- a/src/components/heartrate/Ppg.h
+++ b/src/components/heartrate/Ppg.h
@@ -12,9 +12,9 @@ namespace Pinetime {
public:
Ppg();
int8_t Preprocess(float spl);
- float HeartRate();
+ int HeartRate();
- void SetOffset(uint16_t i);
+ void SetOffset(uint16_t offset);
void Reset();
private:
@@ -25,7 +25,7 @@ namespace Pinetime {
Ptagc agc;
Biquad lpf;
- float ProcessHeartRate();
+ int ProcessHeartRate();
};
}
}
diff --git a/src/components/heartrate/Ptagc.cpp b/src/components/heartrate/Ptagc.cpp
index 1c60bc23..221be460 100644
--- a/src/components/heartrate/Ptagc.cpp
+++ b/src/components/heartrate/Ptagc.cpp
@@ -14,13 +14,15 @@ Ptagc::Ptagc(float start, float decay, float threshold) : peak {start}, decay {d
}
float Ptagc::Step(float spl) {
- if (std::abs(spl) > peak)
+ if (std::abs(spl) > peak) {
peak *= boost;
- else
+ } else {
peak *= decay;
+ }
- if ((spl > (peak * threshold)) || (spl < (peak * -threshold)))
+ if ((spl > (peak * threshold)) || (spl < (peak * -threshold))) {
return 0.0f;
+ }
spl = 100.0f * spl / (2.0f * peak);
return spl;
diff --git a/src/components/motion/MotionController.cpp b/src/components/motion/MotionController.cpp
index 7dd32127..8ba46814 100644
--- a/src/components/motion/MotionController.cpp
+++ b/src/components/motion/MotionController.cpp
@@ -26,10 +26,9 @@ bool MotionController::Should_RaiseWake(bool isSleeping) {
if (not isSleeping) {
if (y <= 0) {
return false;
- } else {
- lastYForWakeUp = 0;
- return false;
}
+ lastYForWakeUp = 0;
+ return false;
}
if (y >= 0) {
@@ -62,6 +61,7 @@ bool MotionController::Should_ShakeWake(uint16_t thresh) {
lastZForShake = z;
return wake;
}
+
int32_t MotionController::currentShakeSpeed() {
return accumulatedspeed;
}
@@ -69,6 +69,7 @@ int32_t MotionController::currentShakeSpeed() {
void MotionController::IsSensorOk(bool isOk) {
isSensorOk = isOk;
}
+
void MotionController::Init(Pinetime::Drivers::Bma421::DeviceTypes types) {
switch (types) {
case Drivers::Bma421::DeviceTypes::BMA421:
@@ -82,6 +83,7 @@ void MotionController::Init(Pinetime::Drivers::Bma421::DeviceTypes types) {
break;
}
}
+
void MotionController::SetService(Pinetime::Controllers::MotionService* service) {
this->service = service;
}
diff --git a/src/components/motion/MotionController.h b/src/components/motion/MotionController.h
index f80b11b9..857bd45a 100644
--- a/src/components/motion/MotionController.h
+++ b/src/components/motion/MotionController.h
@@ -19,12 +19,15 @@ namespace Pinetime {
int16_t X() const {
return x;
}
+
int16_t Y() const {
return y;
}
+
int16_t Z() const {
return z;
}
+
uint32_t NbSteps() const {
return nbSteps;
}
@@ -32,6 +35,7 @@ namespace Pinetime {
void ResetTrip() {
currentTripSteps = 0;
}
+
uint32_t GetTripSteps() const {
return currentTripSteps;
}
@@ -40,6 +44,7 @@ namespace Pinetime {
bool Should_RaiseWake(bool isSleeping);
int32_t currentShakeSpeed();
void IsSensorOk(bool isOk);
+
bool IsSensorOk() const {
return isSensorOk;
}
diff --git a/src/components/motor/MotorController.cpp b/src/components/motor/MotorController.cpp
index db6103f4..4e392416 100644
--- a/src/components/motor/MotorController.cpp
+++ b/src/components/motor/MotorController.cpp
@@ -34,6 +34,6 @@ void MotorController::StopRinging() {
nrf_gpio_pin_set(PinMap::Motor);
}
-void MotorController::StopMotor(TimerHandle_t xTimer) {
+void MotorController::StopMotor(TimerHandle_t /*xTimer*/) {
nrf_gpio_pin_set(PinMap::Motor);
}
diff --git a/src/components/settings/Settings.h b/src/components/settings/Settings.h
index 93f861f3..d1e71656 100644
--- a/src/components/settings/Settings.h
+++ b/src/components/settings/Settings.h
@@ -45,6 +45,7 @@ namespace Pinetime {
Colors ColorBG = Colors::Black;
PTSGaugeStyle gaugeStyle = PTSGaugeStyle::Full;
};
+
struct WatchFaceInfineat {
bool showSideCover = true;
int colorIndex = 0;
@@ -66,6 +67,7 @@ namespace Pinetime {
}
settings.clockFace = face;
};
+
uint8_t GetClockFace() const {
return settings.clockFace;
};
@@ -76,6 +78,7 @@ namespace Pinetime {
}
settings.chimesOption = chimeOption;
};
+
ChimesOption GetChimeOption() const {
return settings.chimesOption;
};
@@ -85,6 +88,7 @@ namespace Pinetime {
settingsChanged = true;
settings.PTS.ColorTime = colorTime;
};
+
Colors GetPTSColorTime() const {
return settings.PTS.ColorTime;
};
@@ -94,6 +98,7 @@ namespace Pinetime {
settingsChanged = true;
settings.PTS.ColorBar = colorBar;
};
+
Colors GetPTSColorBar() const {
return settings.PTS.ColorBar;
};
@@ -103,6 +108,7 @@ namespace Pinetime {
settingsChanged = true;
settings.PTS.ColorBG = colorBG;
};
+
Colors GetPTSColorBG() const {
return settings.PTS.ColorBG;
};
@@ -113,6 +119,7 @@ namespace Pinetime {
settingsChanged = true;
}
};
+
bool GetInfineatShowSideCover() const {
return settings.watchFaceInfineat.showSideCover;
};
@@ -123,6 +130,7 @@ namespace Pinetime {
settingsChanged = true;
}
};
+
int GetInfineatColorIndex() const {
return settings.watchFaceInfineat.colorIndex;
};
@@ -132,6 +140,7 @@ namespace Pinetime {
settingsChanged = true;
settings.PTS.gaugeStyle = gaugeStyle;
};
+
PTSGaugeStyle GetPTSGaugeStyle() const {
return settings.PTS.gaugeStyle;
};
@@ -147,6 +156,7 @@ namespace Pinetime {
void SetSettingsMenu(uint8_t menu) {
settingsMenu = menu;
};
+
uint8_t GetSettingsMenu() const {
return settingsMenu;
};
@@ -157,6 +167,7 @@ namespace Pinetime {
}
settings.clockType = clocktype;
};
+
ClockType GetClockType() const {
return settings.clockType;
};
@@ -167,6 +178,7 @@ namespace Pinetime {
}
settings.notificationStatus = status;
};
+
Notification GetNotificationStatus() const {
return settings.notificationStatus;
};
@@ -255,6 +267,7 @@ namespace Pinetime {
Pinetime::Controllers::FS& fs;
static constexpr uint32_t settingsVersion = 0x0004;
+
struct SettingsData {
uint32_t version = settingsVersion;
uint32_t stepsGoal = 10000;
diff --git a/src/components/timer/TimerController.h b/src/components/timer/TimerController.h
index 93d8afc6..20f07e82 100644
--- a/src/components/timer/TimerController.h
+++ b/src/components/timer/TimerController.h
@@ -7,6 +7,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
}
+
namespace Controllers {
class TimerController {
diff --git a/src/components/utility/LinearApproximation.h b/src/components/utility/LinearApproximation.h
new file mode 100644
index 00000000..f7104ced
--- /dev/null
+++ b/src/components/utility/LinearApproximation.h
@@ -0,0 +1,41 @@
+#pragma once
+
+#include <cstddef>
+#include <array>
+
+namespace Pinetime {
+ namespace Utility {
+
+ // based on: https://github.com/SHristov92/LinearApproximation/blob/main/Linear.h
+ template <typename Key, typename Value, std::size_t Size> class LinearApproximation {
+ using Point = struct {
+ Key key;
+ Value value;
+ };
+
+ public:
+ LinearApproximation(const std::array<Point, Size>&& sorted_points) : points {sorted_points} {
+ }
+
+ Value GetValue(Key key) const {
+ if (key <= points[0].key) {
+ return points[0].value;
+ }
+
+ for (std::size_t i = 1; i < Size; i++) {
+ const auto& p = points[i];
+ const auto& p_prev = points[i - 1];
+
+ if (key < p.key) {
+ return p_prev.value + (key - p_prev.key) * (p.value - p_prev.value) / (p.key - p_prev.key);
+ }
+ }
+
+ return points[Size - 1].value;
+ }
+
+ private:
+ std::array<Point, Size> points;
+ };
+ }
+}
diff --git a/src/displayapp/Apps.h b/src/displayapp/Apps.h
index 8aad9535..89b05d87 100644
--- a/src/displayapp/Apps.h
+++ b/src/displayapp/Apps.h
@@ -34,8 +34,7 @@ namespace Pinetime {
SettingDisplay,
SettingWakeUp,
SettingSteps,
- SettingSetDate,
- SettingSetTime,
+ SettingSetDateTime,
SettingChimes,
SettingShakeThreshold,
SettingBluetooth,
diff --git a/src/displayapp/DisplayApp.cpp b/src/displayapp/DisplayApp.cpp
index 108e380d..725caaf4 100644
--- a/src/displayapp/DisplayApp.cpp
+++ b/src/displayapp/DisplayApp.cpp
@@ -43,8 +43,7 @@
#include "displayapp/screens/settings/SettingWakeUp.h"
#include "displayapp/screens/settings/SettingDisplay.h"
#include "displayapp/screens/settings/SettingSteps.h"
-#include "displayapp/screens/settings/SettingSetDate.h"
-#include "displayapp/screens/settings/SettingSetTime.h"
+#include "displayapp/screens/settings/SettingSetDateTime.h"
#include "displayapp/screens/settings/SettingChimes.h"
#include "displayapp/screens/settings/SettingShakeThreshold.h"
#include "displayapp/screens/settings/SettingBluetooth.h"
@@ -102,9 +101,9 @@ void DisplayApp::Start(System::BootErrors error) {
bootError = error;
if (error == System::BootErrors::TouchController) {
- LoadApp(Apps::Error, DisplayApp::FullRefreshDirections::None);
+ LoadNewScreen(Apps::Error, DisplayApp::FullRefreshDirections::None);
} else {
- LoadApp(Apps::Clock, DisplayApp::FullRefreshDirections::None);
+ LoadNewScreen(Apps::Clock, DisplayApp::FullRefreshDirections::None);
}
if (pdPASS != xTaskCreate(DisplayApp::Process, "displayapp", 800, this, 0, &taskHandle)) {
@@ -132,7 +131,25 @@ void DisplayApp::InitHw() {
void DisplayApp::Refresh() {
auto LoadPreviousScreen = [this]() {
- LoadApp(returnToApp, returnDirection);
+ FullRefreshDirections returnDirection;
+ switch (appStackDirections.Pop()) {
+ case FullRefreshDirections::Up:
+ returnDirection = FullRefreshDirections::Down;
+ break;
+ case FullRefreshDirections::Down:
+ returnDirection = FullRefreshDirections::Up;
+ break;
+ case FullRefreshDirections::LeftAnim:
+ returnDirection = FullRefreshDirections::RightAnim;
+ break;
+ case FullRefreshDirections::RightAnim:
+ returnDirection = FullRefreshDirections::LeftAnim;
+ break;
+ default:
+ returnDirection = FullRefreshDirections::None;
+ break;
+ }
+ LoadScreen(returnAppStack.Pop(), returnDirection);
};
TickType_t queueTimeout;
@@ -152,7 +169,7 @@ void DisplayApp::Refresh() {
}
Messages msg;
- if (xQueueReceive(msgQueue, &msg, queueTimeout)) {
+ if (xQueueReceive(msgQueue, &msg, queueTimeout) == pdTRUE) {
switch (msg) {
case Messages::DimScreen:
brightnessController.Set(Controllers::BrightnessController::Levels::Low);
@@ -180,14 +197,14 @@ void DisplayApp::Refresh() {
// Screens::Clock::BleConnectionStates::NotConnected);
break;
case Messages::NewNotification:
- LoadApp(Apps::NotificationsPreview, DisplayApp::FullRefreshDirections::Down);
+ LoadNewScreen(Apps::NotificationsPreview, DisplayApp::FullRefreshDirections::Down);
break;
case Messages::TimerDone:
if (currentApp == Apps::Timer) {
auto* timer = static_cast<Screens::Timer*>(currentScreen.get());
timer->Reset();
} else {
- LoadApp(Apps::Timer, DisplayApp::FullRefreshDirections::Down);
+ LoadNewScreen(Apps::Timer, DisplayApp::FullRefreshDirections::Up);
}
break;
case Messages::AlarmTriggered:
@@ -195,11 +212,11 @@ void DisplayApp::Refresh() {
auto* alarm = static_cast<Screens::Alarm*>(currentScreen.get());
alarm->SetAlerting();
} else {
- LoadApp(Apps::Alarm, DisplayApp::FullRefreshDirections::None);
+ LoadNewScreen(Apps::Alarm, DisplayApp::FullRefreshDirections::None);
}
break;
case Messages::ShowPairingKey:
- LoadApp(Apps::PassKey, DisplayApp::FullRefreshDirections::Up);
+ LoadNewScreen(Apps::PassKey, DisplayApp::FullRefreshDirections::Up);
break;
case Messages::TouchEvent: {
if (state != States::Running) {
@@ -209,17 +226,30 @@ void DisplayApp::Refresh() {
if (gesture == TouchEvents::None) {
break;
}
+ auto LoadDirToReturnSwipe = [](DisplayApp::FullRefreshDirections refreshDirection) {
+ switch (refreshDirection) {
+ default:
+ case DisplayApp::FullRefreshDirections::Up:
+ return TouchEvents::SwipeDown;
+ case DisplayApp::FullRefreshDirections::Down:
+ return TouchEvents::SwipeUp;
+ case DisplayApp::FullRefreshDirections::LeftAnim:
+ return TouchEvents::SwipeRight;
+ case DisplayApp::FullRefreshDirections::RightAnim:
+ return TouchEvents::SwipeLeft;
+ }
+ };
if (!currentScreen->OnTouchEvent(gesture)) {
if (currentApp == Apps::Clock) {
switch (gesture) {
case TouchEvents::SwipeUp:
- LoadApp(Apps::Launcher, DisplayApp::FullRefreshDirections::Up);
+ LoadNewScreen(Apps::Launcher, DisplayApp::FullRefreshDirections::Up);
break;
case TouchEvents::SwipeDown:
- LoadApp(Apps::Notifications, DisplayApp::FullRefreshDirections::Down);
+ LoadNewScreen(Apps::Notifications, DisplayApp::FullRefreshDirections::Down);
break;
case TouchEvents::SwipeRight:
- LoadApp(Apps::QuickSettings, DisplayApp::FullRefreshDirections::RightAnim);
+ LoadNewScreen(Apps::QuickSettings, DisplayApp::FullRefreshDirections::RightAnim);
break;
case TouchEvents::DoubleTap:
PushMessageToSystemTask(System::Messages::GoToSleep);
@@ -227,7 +257,7 @@ void DisplayApp::Refresh() {
default:
break;
}
- } else if (returnTouchEvent == gesture) {
+ } else if (gesture == LoadDirToReturnSwipe(appStackDirections.Top())) {
LoadPreviousScreen();
}
} else {
@@ -246,26 +276,28 @@ void DisplayApp::Refresh() {
case Messages::ButtonLongPressed:
if (currentApp != Apps::Clock) {
if (currentApp == Apps::Notifications) {
- LoadApp(Apps::Clock, DisplayApp::FullRefreshDirections::Up);
+ LoadNewScreen(Apps::Clock, DisplayApp::FullRefreshDirections::Up);
} else if (currentApp == Apps::QuickSettings) {
- LoadApp(Apps::Clock, DisplayApp::FullRefreshDirections::LeftAnim);
+ LoadNewScreen(Apps::Clock, DisplayApp::FullRefreshDirections::LeftAnim);
} else {
- LoadApp(Apps::Clock, DisplayApp::FullRefreshDirections::Down);
+ LoadNewScreen(Apps::Clock, DisplayApp::FullRefreshDirections::Down);
}
+ appStackDirections.Reset();
+ returnAppStack.Reset();
}
break;
case Messages::ButtonLongerPressed:
// Create reboot app and open it instead
- LoadApp(Apps::SysInfo, DisplayApp::FullRefreshDirections::Up);
+ LoadNewScreen(Apps::SysInfo, DisplayApp::FullRefreshDirections::Up);
break;
case Messages::ButtonDoubleClicked:
if (currentApp != Apps::Notifications && currentApp != Apps::NotificationsPreview) {
- LoadApp(Apps::Notifications, DisplayApp::FullRefreshDirections::Down);
+ LoadNewScreen(Apps::Notifications, DisplayApp::FullRefreshDirections::Down);
}
break;
case Messages::BleFirmwareUpdateStarted:
- LoadApp(Apps::FirmwareUpdate, DisplayApp::FullRefreshDirections::Down);
+ LoadNewScreen(Apps::FirmwareUpdate, DisplayApp::FullRefreshDirections::Down);
break;
case Messages::BleRadioEnableToggle:
PushMessageToSystemTask(System::Messages::BleRadioEnableToggle);
@@ -275,7 +307,7 @@ void DisplayApp::Refresh() {
// What should happen here?
break;
case Messages::Clock:
- LoadApp(Apps::Clock, DisplayApp::FullRefreshDirections::None);
+ LoadNewScreen(Apps::Clock, DisplayApp::FullRefreshDirections::None);
break;
}
}
@@ -285,7 +317,7 @@ void DisplayApp::Refresh() {
}
if (nextApp != Apps::None) {
- LoadApp(nextApp, nextDirection);
+ LoadNewScreen(nextApp, nextDirection);
nextApp = Apps::None;
}
}
@@ -295,27 +327,28 @@ void DisplayApp::StartApp(Apps app, DisplayApp::FullRefreshDirections direction)
nextDirection = direction;
}
-void DisplayApp::ReturnApp(Apps app, DisplayApp::FullRefreshDirections direction, TouchEvents touchEvent) {
- returnToApp = app;
- returnDirection = direction;
- returnTouchEvent = touchEvent;
+void DisplayApp::LoadNewScreen(Apps app, DisplayApp::FullRefreshDirections direction) {
+ // Don't add the same screen to the stack back to back.
+ // This is mainly to fix an issue with receiving two notifications at the same time
+ // and shouldn't happen otherwise.
+ if (app != currentApp) {
+ returnAppStack.Push(currentApp);
+ appStackDirections.Push(direction);
+ }
+ LoadScreen(app, direction);
}
-void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction) {
+void DisplayApp::LoadScreen(Apps app, DisplayApp::FullRefreshDirections direction) {
touchHandler.CancelTap();
ApplyBrightness();
currentScreen.reset(nullptr);
SetFullRefresh(direction);
- // default return to launcher
- ReturnApp(Apps::Launcher, FullRefreshDirections::Down, TouchEvents::SwipeDown);
-
switch (app) {
case Apps::Launcher:
currentScreen =
std::make_unique<Screens::ApplicationList>(this, settingsController, batteryController, bleController, dateTimeController);
- ReturnApp(Apps::Clock, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::None:
case Apps::Clock:
@@ -332,21 +365,17 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
case Apps::Error:
currentScreen = std::make_unique<Screens::Error>(this, bootError);
- ReturnApp(Apps::Clock, FullRefreshDirections::Down, TouchEvents::None);
break;
case Apps::FirmwareValidation:
currentScreen = std::make_unique<Screens::FirmwareValidation>(this, validator);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::FirmwareUpdate:
currentScreen = std::make_unique<Screens::FirmwareUpdate>(this, bleController);
- ReturnApp(Apps::Clock, FullRefreshDirections::Down, TouchEvents::None);
break;
case Apps::PassKey:
currentScreen = std::make_unique<Screens::PassKey>(this, bleController.GetPairingKey());
- ReturnApp(Apps::Clock, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::Notifications:
@@ -356,7 +385,6 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
motorController,
*systemTask,
Screens::Notifications::Modes::Normal);
- ReturnApp(Apps::Clock, FullRefreshDirections::Up, TouchEvents::SwipeUp);
break;
case Apps::NotificationsPreview:
currentScreen = std::make_unique<Screens::Notifications>(this,
@@ -365,7 +393,6 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
motorController,
*systemTask,
Screens::Notifications::Modes::Preview);
- ReturnApp(Apps::Clock, FullRefreshDirections::Up, TouchEvents::SwipeUp);
break;
case Apps::Timer:
currentScreen = std::make_unique<Screens::Timer>(this, timerController);
@@ -383,55 +410,39 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
motorController,
settingsController,
bleController);
- ReturnApp(Apps::Clock, FullRefreshDirections::LeftAnim, TouchEvents::SwipeLeft);
break;
case Apps::Settings:
currentScreen = std::make_unique<Screens::Settings>(this, settingsController);
- ReturnApp(Apps::QuickSettings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingWatchFace:
currentScreen = std::make_unique<Screens::SettingWatchFace>(this, settingsController, filesystem);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingTimeFormat:
currentScreen = std::make_unique<Screens::SettingTimeFormat>(this, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingWakeUp:
currentScreen = std::make_unique<Screens::SettingWakeUp>(this, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingDisplay:
currentScreen = std::make_unique<Screens::SettingDisplay>(this, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingSteps:
currentScreen = std::make_unique<Screens::SettingSteps>(this, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
- case Apps::SettingSetDate:
- currentScreen = std::make_unique<Screens::SettingSetDate>(this, dateTimeController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
- break;
- case Apps::SettingSetTime:
- currentScreen = std::make_unique<Screens::SettingSetTime>(this, dateTimeController, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
+ case Apps::SettingSetDateTime:
+ currentScreen = std::make_unique<Screens::SettingSetDateTime>(this, dateTimeController, settingsController);
break;
case Apps::SettingChimes:
currentScreen = std::make_unique<Screens::SettingChimes>(this, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingShakeThreshold:
currentScreen = std::make_unique<Screens::SettingShakeThreshold>(this, settingsController, motionController, *systemTask);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SettingBluetooth:
currentScreen = std::make_unique<Screens::SettingBluetooth>(this, settingsController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::BatteryInfo:
currentScreen = std::make_unique<Screens::BatteryInfo>(this, batteryController);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::SysInfo:
currentScreen = std::make_unique<Screens::SystemInfo>(this,
@@ -442,11 +453,9 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
watchdog,
motionController,
touchPanel);
- ReturnApp(Apps::Settings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::FlashLight:
currentScreen = std::make_unique<Screens::FlashLight>(this, *systemTask, brightnessController);
- ReturnApp(Apps::QuickSettings, FullRefreshDirections::Down, TouchEvents::SwipeDown);
break;
case Apps::StopWatch:
currentScreen = std::make_unique<Screens::StopWatch>(this, *systemTask);
@@ -471,7 +480,6 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
break;
case Apps::Metronome:
currentScreen = std::make_unique<Screens::Metronome>(this, motorController, *systemTask);
- ReturnApp(Apps::Launcher, FullRefreshDirections::Down, TouchEvents::None);
break;
case Apps::Motion:
currentScreen = std::make_unique<Screens::Motion>(this, motionController);
@@ -485,10 +493,9 @@ void DisplayApp::LoadApp(Apps app, DisplayApp::FullRefreshDirections direction)
void DisplayApp::PushMessage(Messages msg) {
if (in_isr()) {
- BaseType_t xHigherPriorityTaskWoken;
- xHigherPriorityTaskWoken = pdFALSE;
+ BaseType_t xHigherPriorityTaskWoken = pdFALSE;
xQueueSendFromISR(msgQueue, &msg, &xHigherPriorityTaskWoken);
- if (xHigherPriorityTaskWoken) {
+ if (xHigherPriorityTaskWoken == pdTRUE) {
portYIELD_FROM_ISR(xHigherPriorityTaskWoken);
}
} else {
@@ -530,10 +537,10 @@ void DisplayApp::PushMessageToSystemTask(Pinetime::System::Messages message) {
void DisplayApp::Register(Pinetime::System::SystemTask* systemTask) {
this->systemTask = systemTask;
}
+
void DisplayApp::ApplyBrightness() {
auto brightness = settingsController.GetBrightness();
- if(brightness != Controllers::BrightnessController::Levels::Low &&
- brightness != Controllers::BrightnessController::Levels::Medium &&
+ if (brightness != Controllers::BrightnessController::Levels::Low && brightness != Controllers::BrightnessController::Levels::Medium &&
brightness != Controllers::BrightnessController::Levels::High) {
brightness = Controllers::BrightnessController::Levels::High;
}
diff --git a/src/displayapp/DisplayApp.h b/src/displayapp/DisplayApp.h
index 4c54e227..c1d04cc9 100644
--- a/src/displayapp/DisplayApp.h
+++ b/src/displayapp/DisplayApp.h
@@ -20,6 +20,8 @@
#include "displayapp/Messages.h"
#include "BootErrors.h"
+#include "StaticStack.h"
+
namespace Pinetime {
namespace Drivers {
@@ -27,6 +29,7 @@ namespace Pinetime {
class Cst816S;
class WatchdogView;
}
+
namespace Controllers {
class Settings;
class Battery;
@@ -41,6 +44,7 @@ namespace Pinetime {
namespace System {
class SystemTask;
};
+
namespace Applications {
class DisplayApp {
public:
@@ -114,14 +118,18 @@ namespace Pinetime {
static void Process(void* instance);
void InitHw();
void Refresh();
- void ReturnApp(Apps app, DisplayApp::FullRefreshDirections direction, TouchEvents touchEvent);
- void LoadApp(Apps app, DisplayApp::FullRefreshDirections direction);
+ void LoadNewScreen(Apps app, DisplayApp::FullRefreshDirections direction);
+ void LoadScreen(Apps app, DisplayApp::FullRefreshDirections direction);
void PushMessageToSystemTask(Pinetime::System::Messages message);
Apps nextApp = Apps::None;
DisplayApp::FullRefreshDirections nextDirection;
System::BootErrors bootError;
void ApplyBrightness();
+
+ static constexpr size_t returnAppStackSize = 10;
+ StaticStack<Apps, returnAppStackSize> returnAppStack;
+ StaticStack<FullRefreshDirections, returnAppStackSize> appStackDirections;
};
}
}
diff --git a/src/displayapp/DisplayAppRecovery.cpp b/src/displayapp/DisplayAppRecovery.cpp
index e553aa87..ecc01e9b 100644
--- a/src/displayapp/DisplayAppRecovery.cpp
+++ b/src/displayapp/DisplayAppRecovery.cpp
@@ -11,22 +11,22 @@
using namespace Pinetime::Applications;
DisplayApp::DisplayApp(Drivers::St7789& lcd,
- Components::LittleVgl& lvgl,
- Drivers::Cst816S& touchPanel,
- Controllers::Battery& batteryController,
+ Components::LittleVgl& /*lvgl*/,
+ Drivers::Cst816S& /*touchPanel*/,
+ Controllers::Battery& /*batteryController*/,
Controllers::Ble& bleController,
- Controllers::DateTime& dateTimeController,
- Drivers::WatchdogView& watchdog,
- Pinetime::Controllers::NotificationManager& notificationManager,
- Pinetime::Controllers::HeartRateController& heartRateController,
- Controllers::Settings& settingsController,
- Pinetime::Controllers::MotorController& motorController,
- Pinetime::Controllers::MotionController& motionController,
- Pinetime::Controllers::TimerController& timerController,
- Pinetime::Controllers::AlarmController& alarmController,
- Pinetime::Controllers::BrightnessController& brightnessController,
- Pinetime::Controllers::TouchHandler& touchHandler,
- Pinetime::Controllers::FS& filesystem)
+ Controllers::DateTime& /*dateTimeController*/,
+ Drivers::WatchdogView& /*watchdog*/,
+ Pinetime::Controllers::NotificationManager& /*notificationManager*/,
+ Pinetime::Controllers::HeartRateController& /*heartRateController*/,
+ Controllers::Settings& /*settingsController*/,
+ Pinetime::Controllers::MotorController& /*motorController*/,
+ Pinetime::Controllers::MotionController& /*motionController*/,
+ Pinetime::Controllers::TimerController& /*timerController*/,
+ Pinetime::Controllers::AlarmController& /*alarmController*/,
+ Pinetime::Controllers::BrightnessController& /*brightnessController*/,
+ Pinetime::Controllers::TouchHandler& /*touchHandler*/,
+ Pinetime::Controllers::FS& /*filesystem*/)
: lcd {lcd}, bleController {bleController} {
}
@@ -121,5 +121,5 @@ void DisplayApp::PushMessage(Display::Messages msg) {
}
}
-void DisplayApp::Register(Pinetime::System::SystemTask* systemTask) {
+void DisplayApp::Register(Pinetime::System::SystemTask* /*systemTask*/) {
}
diff --git a/src/displayapp/DisplayAppRecovery.h b/src/displayapp/DisplayAppRecovery.h
index 7d4f0fd0..97aaca88 100644
--- a/src/displayapp/DisplayAppRecovery.h
+++ b/src/displayapp/DisplayAppRecovery.h
@@ -22,6 +22,7 @@ namespace Pinetime {
class Cst816S;
class WatchdogView;
}
+
namespace Controllers {
class Settings;
class Battery;
@@ -63,9 +64,11 @@ namespace Pinetime {
Pinetime::Controllers::TouchHandler& touchHandler,
Pinetime::Controllers::FS& filesystem);
void Start();
+
void Start(Pinetime::System::BootErrors) {
Start();
};
+
void PushMessage(Pinetime::Applications::Display::Messages msg);
void Register(Pinetime::System::SystemTask* systemTask);
diff --git a/src/displayapp/DummyLittleVgl.h b/src/displayapp/DummyLittleVgl.h
index 05355a97..7a8ae999 100644
--- a/src/displayapp/DummyLittleVgl.h
+++ b/src/displayapp/DummyLittleVgl.h
@@ -11,6 +11,7 @@ namespace Pinetime {
class LittleVgl {
public:
enum class FullRefreshDirections { None, Up, Down };
+
LittleVgl(Pinetime::Drivers::St7789& lcd, Pinetime::Drivers::Cst816S& touchPanel) {
}
@@ -24,13 +25,17 @@ namespace Pinetime {
void FlushDisplay(const lv_area_t* area, lv_color_t* color_p) {
}
+
bool GetTouchPadInfo(lv_indev_data_t* ptr) {
return false;
}
+
void SetFullRefresh(FullRefreshDirections direction) {
}
+
void SetNewTapEvent(uint16_t x, uint16_t y) {
}
+
void SetNewTouchPoint(uint16_t x, uint16_t y, bool contact) {
}
};
diff --git a/src/displayapp/InfiniTimeTheme.cpp b/src/displayapp/InfiniTimeTheme.cpp
index 4290d87f..6795647e 100644
--- a/src/displayapp/InfiniTimeTheme.cpp
+++ b/src/displayapp/InfiniTimeTheme.cpp
@@ -1,4 +1,17 @@
#include "displayapp/InfiniTimeTheme.h"
+#include <algorithm>
+
+// Replace LV_DPX with a constexpr version using a constant LV_DPI
+#undef LV_DPX
+
+namespace {
+ constexpr int LV_DPX(int n) {
+ if (n == 0) {
+ return 0;
+ }
+ return std::max(((LV_DPI * n + 80) / 160), 1); /*+80 for rounding*/
+ }
+}
static void theme_apply(lv_obj_t* obj, lv_theme_style_t name);
@@ -47,7 +60,6 @@ static void basic_init() {
style_init_reset(&style_box);
lv_style_set_bg_opa(&style_box, LV_STATE_DEFAULT, LV_OPA_COVER);
lv_style_set_radius(&style_box, LV_STATE_DEFAULT, 10);
- lv_style_set_value_color(&style_box, LV_STATE_DEFAULT, Colors::bg);
lv_style_set_value_font(&style_box, LV_STATE_DEFAULT, theme.font_normal);
style_init_reset(&style_label_white);
@@ -60,25 +72,12 @@ static void basic_init() {
lv_style_set_bg_color(&style_btn, LV_STATE_DEFAULT, Colors::bg);
lv_style_set_bg_color(&style_btn, LV_STATE_CHECKED, Colors::highlight);
lv_style_set_bg_color(&style_btn, LV_STATE_DISABLED, Colors::bgDark);
- lv_style_set_border_color(&style_btn, LV_STATE_DEFAULT, LV_COLOR_WHITE);
- lv_style_set_border_width(&style_btn, LV_STATE_DEFAULT, 0);
lv_style_set_text_color(&style_btn, LV_STATE_DEFAULT, LV_COLOR_WHITE);
lv_style_set_text_color(&style_btn, LV_STATE_DISABLED, LV_COLOR_GRAY);
- lv_style_set_value_color(&style_btn, LV_STATE_DEFAULT, LV_COLOR_WHITE);
- lv_style_set_value_color(&style_btn, LV_STATE_DISABLED, LV_COLOR_GRAY);
-
- lv_style_set_pad_left(&style_btn, LV_STATE_DEFAULT, LV_DPX(20));
- lv_style_set_pad_right(&style_btn, LV_STATE_DEFAULT, LV_DPX(20));
- lv_style_set_pad_top(&style_btn, LV_STATE_DEFAULT, LV_DPX(20));
- lv_style_set_pad_bottom(&style_btn, LV_STATE_DEFAULT, LV_DPX(20));
+ lv_style_set_pad_all(&style_btn, LV_STATE_DEFAULT, LV_DPX(20));
lv_style_set_pad_inner(&style_btn, LV_STATE_DEFAULT, LV_DPX(15));
- lv_style_set_outline_width(&style_btn, LV_STATE_DEFAULT, LV_DPX(2));
- lv_style_set_outline_opa(&style_btn, LV_STATE_DEFAULT, LV_OPA_0);
- lv_style_set_outline_color(&style_btn, LV_STATE_DEFAULT, LV_COLOR_WHITE);
- lv_style_set_transition_time(&style_btn, LV_STATE_DEFAULT, 0);
- lv_style_set_transition_delay(&style_btn, LV_STATE_DEFAULT, 0);
style_init_reset(&style_icon);
lv_style_set_text_color(&style_icon, LV_STATE_DEFAULT, LV_COLOR_WHITE);
@@ -132,10 +131,7 @@ static void basic_init() {
lv_style_set_bg_color(&style_sw_knob, LV_STATE_DEFAULT, LV_COLOR_SILVER);
lv_style_set_bg_color(&style_sw_knob, LV_STATE_CHECKED, LV_COLOR_WHITE);
lv_style_set_radius(&style_sw_knob, LV_STATE_DEFAULT, LV_RADIUS_CIRCLE);
- lv_style_set_pad_top(&style_sw_knob, LV_STATE_DEFAULT, -4);
- lv_style_set_pad_bottom(&style_sw_knob, LV_STATE_DEFAULT, -4);
- lv_style_set_pad_left(&style_sw_knob, LV_STATE_DEFAULT, -4);
- lv_style_set_pad_right(&style_sw_knob, LV_STATE_DEFAULT, -4);
+ lv_style_set_pad_all(&style_sw_knob, LV_STATE_DEFAULT, -4);
style_init_reset(&style_slider_knob);
lv_style_set_bg_opa(&style_slider_knob, LV_STATE_DEFAULT, LV_OPA_COVER);
@@ -143,14 +139,8 @@ static void basic_init() {
lv_style_set_border_color(&style_slider_knob, LV_STATE_DEFAULT, LV_COLOR_WHITE);
lv_style_set_border_width(&style_slider_knob, LV_STATE_DEFAULT, 6);
lv_style_set_radius(&style_slider_knob, LV_STATE_DEFAULT, LV_RADIUS_CIRCLE);
- lv_style_set_pad_top(&style_slider_knob, LV_STATE_DEFAULT, 10);
- lv_style_set_pad_bottom(&style_slider_knob, LV_STATE_DEFAULT, 10);
- lv_style_set_pad_left(&style_slider_knob, LV_STATE_DEFAULT, 10);
- lv_style_set_pad_right(&style_slider_knob, LV_STATE_DEFAULT, 10);
- lv_style_set_pad_top(&style_slider_knob, LV_STATE_PRESSED, 14);
- lv_style_set_pad_bottom(&style_slider_knob, LV_STATE_PRESSED, 14);
- lv_style_set_pad_left(&style_slider_knob, LV_STATE_PRESSED, 14);
- lv_style_set_pad_right(&style_slider_knob, LV_STATE_PRESSED, 14);
+ lv_style_set_pad_all(&style_slider_knob, LV_STATE_DEFAULT, 10);
+ lv_style_set_pad_all(&style_slider_knob, LV_STATE_PRESSED, 14);
style_init_reset(&style_arc_indic);
lv_style_set_line_color(&style_arc_indic, LV_STATE_DEFAULT, Colors::lightGray);
@@ -180,10 +170,7 @@ static void basic_init() {
style_init_reset(&style_pad_small);
lv_style_int_t pad_small_value = 10;
- lv_style_set_pad_left(&style_pad_small, LV_STATE_DEFAULT, pad_small_value);
- lv_style_set_pad_right(&style_pad_small, LV_STATE_DEFAULT, pad_small_value);
- lv_style_set_pad_top(&style_pad_small, LV_STATE_DEFAULT, pad_small_value);
- lv_style_set_pad_bottom(&style_pad_small, LV_STATE_DEFAULT, pad_small_value);
+ lv_style_set_pad_all(&style_pad_small, LV_STATE_DEFAULT, pad_small_value);
lv_style_set_pad_inner(&style_pad_small, LV_STATE_DEFAULT, pad_small_value);
style_init_reset(&style_lmeter);
@@ -209,20 +196,12 @@ static void basic_init() {
lv_style_reset(&style_cb_bg);
lv_style_set_radius(&style_cb_bg, LV_STATE_DEFAULT, LV_DPX(4));
lv_style_set_pad_inner(&style_cb_bg, LV_STATE_DEFAULT, 18);
- lv_style_set_outline_color(&style_cb_bg, LV_STATE_DEFAULT, LV_COLOR_WHITE);
- lv_style_set_outline_width(&style_cb_bg, LV_STATE_DEFAULT, LV_DPX(2));
- lv_style_set_outline_pad(&style_cb_bg, LV_STATE_DEFAULT, LV_DPX(20));
- lv_style_set_transition_time(&style_cb_bg, LV_STATE_DEFAULT, 0);
- lv_style_set_transition_prop_6(&style_cb_bg, LV_STATE_DEFAULT, LV_STYLE_OUTLINE_OPA);
lv_style_reset(&style_cb_bullet);
lv_style_set_radius(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(4));
lv_style_set_pattern_image(&style_cb_bullet, LV_STATE_CHECKED, LV_SYMBOL_OK);
lv_style_set_pattern_recolor(&style_cb_bullet, LV_STATE_CHECKED, LV_COLOR_WHITE);
- lv_style_set_pad_left(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
- lv_style_set_pad_right(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
- lv_style_set_pad_top(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
- lv_style_set_pad_bottom(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
+ lv_style_set_pad_all(&style_cb_bullet, LV_STATE_DEFAULT, LV_DPX(8));
}
/**
@@ -236,20 +215,14 @@ static void basic_init() {
* @param font_title pointer to a extra large font
* @return a pointer to reference this theme later
*/
-lv_theme_t* lv_pinetime_theme_init(lv_color_t color_primary,
- lv_color_t color_secondary,
- uint32_t flags,
- const lv_font_t* font_small,
- const lv_font_t* font_normal,
- const lv_font_t* font_subtitle,
- const lv_font_t* font_title) {
- theme.color_primary = color_primary;
- theme.color_secondary = color_secondary;
- theme.font_small = font_small;
- theme.font_normal = font_normal;
- theme.font_subtitle = font_subtitle;
- theme.font_title = font_title;
- theme.flags = flags;
+lv_theme_t* lv_pinetime_theme_init() {
+ theme.color_primary = LV_COLOR_WHITE;
+ theme.color_secondary = LV_COLOR_GRAY;
+ theme.font_small = &jetbrains_mono_bold_20;
+ theme.font_normal = &jetbrains_mono_bold_20;
+ theme.font_subtitle = &jetbrains_mono_bold_20;
+ theme.font_title = &jetbrains_mono_bold_20;
+ theme.flags = 0;
basic_init();
diff --git a/src/displayapp/InfiniTimeTheme.h b/src/displayapp/InfiniTimeTheme.h
index 5709b007..52c339dd 100644
--- a/src/displayapp/InfiniTimeTheme.h
+++ b/src/displayapp/InfiniTimeTheme.h
@@ -24,10 +24,4 @@ namespace Colors {
* @param font_title pointer to a extra large font
* @return a pointer to reference this theme later
*/
-lv_theme_t* lv_pinetime_theme_init(lv_color_t color_primary,
- lv_color_t color_secondary,
- uint32_t flags,
- const lv_font_t* font_small,
- const lv_font_t* font_normal,
- const lv_font_t* font_subtitle,
- const lv_font_t* font_title);
+lv_theme_t* lv_pinetime_theme_init();
diff --git a/src/displayapp/LittleVgl.cpp b/src/displayapp/LittleVgl.cpp
index d5f31848..e3d564a3 100644
--- a/src/displayapp/LittleVgl.cpp
+++ b/src/displayapp/LittleVgl.cpp
@@ -3,13 +3,17 @@
#include <FreeRTOS.h>
#include <task.h>
-//#include <projdefs.h>
#include "drivers/Cst816s.h"
#include "drivers/St7789.h"
using namespace Pinetime::Components;
-lv_style_t* LabelBigStyle = nullptr;
+namespace {
+ void InitTheme() {
+ lv_theme_t* theme = lv_pinetime_theme_init();
+ lv_theme_set_act(theme);
+ }
+}
static void disp_flush(lv_disp_drv_t* disp_drv, const lv_area_t* area, lv_color_t* color_p) {
auto* lvgl = static_cast<LittleVgl*>(disp_drv->user_data);
@@ -192,16 +196,3 @@ bool LittleVgl::GetTouchPadInfo(lv_indev_data_t* ptr) {
}
return false;
}
-
-void LittleVgl::InitTheme() {
-
- lv_theme_t* th = lv_pinetime_theme_init(LV_COLOR_WHITE,
- LV_COLOR_SILVER,
- 0,
- &jetbrains_mono_bold_20,
- &jetbrains_mono_bold_20,
- &jetbrains_mono_bold_20,
- &jetbrains_mono_bold_20);
-
- lv_theme_set_act(th);
-}
diff --git a/src/displayapp/LittleVgl.h b/src/displayapp/LittleVgl.h
index 45826165..7bd0198c 100644
--- a/src/displayapp/LittleVgl.h
+++ b/src/displayapp/LittleVgl.h
@@ -37,7 +37,6 @@ namespace Pinetime {
private:
void InitDisplay();
void InitTouchpad();
- void InitTheme();
Pinetime::Drivers::St7789& lcd;
Pinetime::Drivers::Cst816S& touchPanel;
@@ -52,9 +51,11 @@ namespace Pinetime {
static constexpr uint8_t nbWriteLines = 4;
static constexpr uint16_t totalNbLines = 320;
static constexpr uint16_t visibleNbLines = 240;
+
static constexpr uint8_t MaxScrollOffset() {
return LV_VER_RES_MAX - nbWriteLines;
}
+
FullRefreshDirections scrollDirection = FullRefreshDirections::None;
uint16_t writeOffset = 0;
uint16_t scrollOffset = 0;
diff --git a/src/displayapp/Messages.h b/src/displayapp/Messages.h
index 58df4556..afa7709a 100644
--- a/src/displayapp/Messages.h
+++ b/src/displayapp/Messages.h
@@ -1,5 +1,6 @@
#pragma once
#include <cstdint>
+
namespace Pinetime {
namespace Applications {
namespace Display {
diff --git a/src/displayapp/screens/BatteryInfo.cpp b/src/displayapp/screens/BatteryInfo.cpp
index 9febda61..87d1f2e1 100644
--- a/src/displayapp/screens/BatteryInfo.cpp
+++ b/src/displayapp/screens/BatteryInfo.cpp
@@ -59,7 +59,7 @@ void BatteryInfo::Refresh() {
} else if (batteryPercent == 100) {
lv_obj_set_style_local_bg_color(charging_bar, LV_BAR_PART_INDIC, LV_STATE_DEFAULT, LV_COLOR_BLUE);
lv_label_set_text_static(status, "Fully charged");
- } else if (batteryPercent < 10) {
+ } else if (batteryController.BatteryIsLow()) {
lv_obj_set_style_local_bg_color(charging_bar, LV_BAR_PART_INDIC, LV_STATE_DEFAULT, LV_COLOR_YELLOW);
lv_label_set_text_static(status, "Battery low");
} else {
diff --git a/src/displayapp/screens/CheckboxList.cpp b/src/displayapp/screens/CheckboxList.cpp
index c189b075..928b2e61 100644
--- a/src/displayapp/screens/CheckboxList.cpp
+++ b/src/displayapp/screens/CheckboxList.cpp
@@ -28,7 +28,9 @@ CheckboxList::CheckboxList(const uint8_t screenID,
// Set the background to Black
lv_obj_set_style_local_bg_color(lv_scr_act(), LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_BLACK);
- pageIndicator.Create();
+ if (numScreens > 1) {
+ pageIndicator.Create();
+ }
lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
diff --git a/src/displayapp/screens/CheckboxList.h b/src/displayapp/screens/CheckboxList.h
index 48125d4b..359b835e 100644
--- a/src/displayapp/screens/CheckboxList.h
+++ b/src/displayapp/screens/CheckboxList.h
@@ -15,6 +15,7 @@ namespace Pinetime {
class CheckboxList : public Screen {
public:
static constexpr size_t MaxItems = 4;
+
struct Item {
const char* name;
bool enabled;
diff --git a/src/displayapp/screens/FirmwareUpdate.h b/src/displayapp/screens/FirmwareUpdate.h
index 5156b7ea..cc3b09b2 100644
--- a/src/displayapp/screens/FirmwareUpdate.h
+++ b/src/displayapp/screens/FirmwareUpdate.h
@@ -8,6 +8,7 @@ namespace Pinetime {
namespace Controllers {
class Ble;
}
+
namespace Applications {
namespace Screens {
diff --git a/src/displayapp/screens/FirmwareValidation.cpp b/src/displayapp/screens/FirmwareValidation.cpp
index a2314690..bda6d68d 100644
--- a/src/displayapp/screens/FirmwareValidation.cpp
+++ b/src/displayapp/screens/FirmwareValidation.cpp
@@ -32,16 +32,16 @@ FirmwareValidation::FirmwareValidation(Pinetime::Applications::DisplayApp* app,
lv_label_set_long_mode(labelIsValidated, LV_LABEL_LONG_BREAK);
lv_obj_set_width(labelIsValidated, 240);
- if (validator.IsValidated())
+ if (validator.IsValidated()) {
lv_label_set_text_static(labelIsValidated, "You have already\n#00ff00 validated# this firmware#");
- else {
+ } else {
lv_label_set_text_static(labelIsValidated,
"Please #00ff00 Validate# this version or\n#ff0000 Reset# to rollback to the previous version.");
buttonValidate = lv_btn_create(lv_scr_act(), nullptr);
buttonValidate->user_data = this;
lv_obj_set_size(buttonValidate, 115, 50);
- lv_obj_align(buttonValidate, NULL, LV_ALIGN_IN_BOTTOM_LEFT, 0, 0);
+ lv_obj_align(buttonValidate, nullptr, LV_ALIGN_IN_BOTTOM_LEFT, 0, 0);
lv_obj_set_event_cb(buttonValidate, ButtonEventHandler);
lv_obj_set_style_local_bg_color(buttonValidate, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, Colors::highlight);
diff --git a/src/displayapp/screens/HeartRate.cpp b/src/displayapp/screens/HeartRate.cpp
index 305e0c4b..71bf86ca 100644
--- a/src/displayapp/screens/HeartRate.cpp
+++ b/src/displayapp/screens/HeartRate.cpp
@@ -64,8 +64,9 @@ HeartRate::HeartRate(Pinetime::Applications::DisplayApp* app,
label_startStop = lv_label_create(btn_startStop, nullptr);
UpdateStartStopButton(isHrRunning);
- if (isHrRunning)
+ if (isHrRunning) {
systemTask.PushMessage(Pinetime::System::Messages::DisableSleeping);
+ }
taskRefresh = lv_task_create(RefreshTaskCallback, 100, LV_TASK_PRIO_MID, this);
}
@@ -110,8 +111,9 @@ void HeartRate::OnStartStopEvent(lv_event_t event) {
}
void HeartRate::UpdateStartStopButton(bool isRunning) {
- if (isRunning)
+ if (isRunning) {
lv_label_set_text_static(label_startStop, "Stop");
- else
+ } else {
lv_label_set_text_static(label_startStop, "Start");
+ }
}
diff --git a/src/displayapp/screens/HeartRate.h b/src/displayapp/screens/HeartRate.h
index 2ad00351..d68133ad 100644
--- a/src/displayapp/screens/HeartRate.h
+++ b/src/displayapp/screens/HeartRate.h
@@ -11,6 +11,7 @@ namespace Pinetime {
namespace Controllers {
class HeartRateController;
}
+
namespace Applications {
namespace Screens {
diff --git a/src/displayapp/screens/InfiniPaint.h b/src/displayapp/screens/InfiniPaint.h
index 8c427402..a6b6eb18 100644
--- a/src/displayapp/screens/InfiniPaint.h
+++ b/src/displayapp/screens/InfiniPaint.h
@@ -10,6 +10,7 @@ namespace Pinetime {
namespace Components {
class LittleVgl;
}
+
namespace Applications {
namespace Screens {
diff --git a/src/displayapp/screens/List.cpp b/src/displayapp/screens/List.cpp
index f44825c7..3f219ea1 100644
--- a/src/displayapp/screens/List.cpp
+++ b/src/displayapp/screens/List.cpp
@@ -1,6 +1,7 @@
#include "displayapp/screens/List.h"
#include "displayapp/DisplayApp.h"
#include "displayapp/screens/Symbols.h"
+#include "displayapp/InfiniTimeTheme.h"
using namespace Pinetime::Applications::Screens;
@@ -25,41 +26,44 @@ List::List(uint8_t screenID,
pageIndicator.Create();
- lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
+ lv_obj_t* container = lv_cont_create(lv_scr_act(), nullptr);
- lv_obj_set_style_local_bg_opa(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
- lv_obj_set_style_local_pad_inner(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 4);
- lv_obj_set_style_local_border_width(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 0);
+ lv_obj_set_style_local_bg_opa(container, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
+ static constexpr int innerPad = 4;
+ lv_obj_set_style_local_pad_inner(container, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, innerPad);
+ lv_obj_set_style_local_border_width(container, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 0);
- lv_obj_set_pos(container1, 0, 0);
- lv_obj_set_width(container1, LV_HOR_RES - 8);
- lv_obj_set_height(container1, LV_VER_RES);
- lv_cont_set_layout(container1, LV_LAYOUT_COLUMN_LEFT);
-
- lv_obj_t* labelBt;
- lv_obj_t* labelBtIco;
+ lv_obj_set_pos(container, 0, 0);
+ lv_obj_set_width(container, LV_HOR_RES - 8);
+ lv_obj_set_height(container, LV_VER_RES);
+ lv_cont_set_layout(container, LV_LAYOUT_COLUMN_LEFT);
for (int i = 0; i < MAXLISTITEMS; i++) {
apps[i] = applications[i].application;
if (applications[i].application != Apps::None) {
- itemApps[i] = lv_btn_create(container1, nullptr);
- lv_obj_set_style_local_bg_opa(itemApps[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_50);
- lv_obj_set_style_local_radius(itemApps[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, 57);
- lv_obj_set_style_local_bg_color(itemApps[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_AQUA);
-
+ static constexpr int btnHeight = (LV_HOR_RES_MAX - ((MAXLISTITEMS - 1) * innerPad)) / MAXLISTITEMS;
+ itemApps[i] = lv_btn_create(container, nullptr);
+ lv_obj_set_style_local_radius(itemApps[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, btnHeight / 3);
+ lv_obj_set_style_local_bg_color(itemApps[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, Colors::bgAlt);
lv_obj_set_width(itemApps[i], LV_HOR_RES - 8);
- lv_obj_set_height(itemApps[i], 57);
+ lv_obj_set_height(itemApps[i], btnHeight);
lv_obj_set_event_cb(itemApps[i], ButtonEventHandler);
- lv_btn_set_layout(itemApps[i], LV_LAYOUT_ROW_MID);
+ lv_btn_set_layout(itemApps[i], LV_LAYOUT_OFF);
itemApps[i]->user_data = this;
+ lv_obj_set_style_local_clip_corner(itemApps[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, true);
- labelBtIco = lv_label_create(itemApps[i], nullptr);
- lv_obj_set_style_local_text_color(labelBtIco, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_YELLOW);
- lv_label_set_text_static(labelBtIco, applications[i].icon);
+ lv_obj_t* icon = lv_label_create(itemApps[i], nullptr);
+ lv_obj_set_style_local_text_color(icon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_YELLOW);
+ lv_label_set_text_static(icon, applications[i].icon);
+ lv_label_set_long_mode(icon, LV_LABEL_LONG_CROP);
+ lv_label_set_align(icon, LV_LABEL_ALIGN_CENTER);
+ lv_obj_set_width(icon, btnHeight);
+ lv_obj_align(icon, nullptr, LV_ALIGN_IN_LEFT_MID, 0, 0);
- labelBt = lv_label_create(itemApps[i], nullptr);
- lv_label_set_text_fmt(labelBt, " %s", applications[i].name);
+ lv_obj_t* text = lv_label_create(itemApps[i], nullptr);
+ lv_label_set_text_fmt(text, "%s", applications[i].name);
+ lv_obj_align(text, icon, LV_ALIGN_OUT_RIGHT_MID, 0, 0);
}
}
}
diff --git a/src/displayapp/screens/Metronome.cpp b/src/displayapp/screens/Metronome.cpp
index df87092b..40456ab8 100644
--- a/src/displayapp/screens/Metronome.cpp
+++ b/src/displayapp/screens/Metronome.cpp
@@ -146,7 +146,6 @@ void Metronome::OnEvent(lv_obj_t* obj, lv_event_t event) {
bool Metronome::OnTouchEvent(TouchEvents event) {
if (event == TouchEvents::SwipeDown && allowExit) {
running = false;
- return true;
}
- return false;
+ return true;
}
diff --git a/src/displayapp/screens/Motion.cpp b/src/displayapp/screens/Motion.cpp
index c2dc4dac..e3689599 100644
--- a/src/displayapp/screens/Motion.cpp
+++ b/src/displayapp/screens/Motion.cpp
@@ -7,9 +7,9 @@ using namespace Pinetime::Applications::Screens;
Motion::Motion(Pinetime::Applications::DisplayApp* app, Controllers::MotionController& motionController)
: Screen(app), motionController {motionController} {
- chart = lv_chart_create(lv_scr_act(), NULL);
+ chart = lv_chart_create(lv_scr_act(), nullptr);
lv_obj_set_size(chart, 240, 240);
- lv_obj_align(chart, NULL, LV_ALIGN_IN_TOP_MID, 0, 0);
+ lv_obj_align(chart, nullptr, LV_ALIGN_IN_TOP_MID, 0, 0);
lv_chart_set_type(chart, LV_CHART_TYPE_LINE); /*Show lines and points too*/
// lv_chart_set_series_opa(chart, LV_OPA_70); /*Opacity of the data series*/
// lv_chart_set_series_width(chart, 4); /*Line width and point radious*/
@@ -28,13 +28,13 @@ Motion::Motion(Pinetime::Applications::DisplayApp* app, Controllers::MotionContr
lv_chart_init_points(chart, ser3, 0);
lv_chart_refresh(chart); /*Required after direct set*/
- label = lv_label_create(lv_scr_act(), NULL);
+ label = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_text_fmt(label, "X #FF0000 %d# Y #00B000 %d# Z #FFFF00 %d#", 0, 0, 0);
lv_label_set_align(label, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(label, NULL, LV_ALIGN_IN_TOP_MID, 0, 10);
+ lv_obj_align(label, nullptr, LV_ALIGN_IN_TOP_MID, 0, 10);
lv_label_set_recolor(label, true);
- labelStep = lv_label_create(lv_scr_act(), NULL);
+ labelStep = lv_label_create(lv_scr_act(), nullptr);
lv_obj_align(labelStep, chart, LV_ALIGN_IN_BOTTOM_LEFT, 0, 0);
lv_label_set_text_static(labelStep, "Steps ---");
@@ -58,5 +58,5 @@ void Motion::Refresh() {
motionController.X() / 0x10,
motionController.Y() / 0x10,
motionController.Z() / 0x10);
- lv_obj_align(label, NULL, LV_ALIGN_IN_TOP_MID, 0, 10);
+ lv_obj_align(label, nullptr, LV_ALIGN_IN_TOP_MID, 0, 10);
}
diff --git a/src/displayapp/screens/Notifications.cpp b/src/displayapp/screens/Notifications.cpp
index 90a010f5..6c68c70d 100644
--- a/src/displayapp/screens/Notifications.cpp
+++ b/src/displayapp/screens/Notifications.cpp
@@ -79,9 +79,12 @@ void Notifications::Refresh() {
timeoutLinePoints[1].x = pos;
lv_line_set_points(timeoutLine, timeoutLinePoints, 2);
}
- }
- if (dismissingNotification) {
+ } else if (mode == Modes::Preview && dismissingNotification) {
+ running = false;
+ currentItem = std::make_unique<NotificationItem>(alertNotificationService, motorController);
+
+ } else if (dismissingNotification) {
dismissingNotification = false;
auto notification = notificationManager.Get(currentId);
if (!notification.valid) {
@@ -126,12 +129,34 @@ void Notifications::OnPreviewInteraction() {
}
}
+void Notifications::DismissToBlack() {
+ currentItem.reset(nullptr);
+ app->SetFullRefresh(DisplayApp::FullRefreshDirections::RightAnim);
+ // create black transition screen to let the notification dismiss to blackness
+ lv_obj_t* blackBox = lv_obj_create(lv_scr_act(), nullptr);
+ lv_obj_set_size(blackBox, LV_HOR_RES, LV_VER_RES);
+ lv_obj_set_style_local_bg_color(blackBox, LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_BLACK);
+ dismissingNotification = true;
+}
+
+void Notifications::OnPreviewDismiss() {
+ notificationManager.Dismiss(currentId);
+ if (timeoutLine != nullptr) {
+ lv_obj_del(timeoutLine);
+ timeoutLine = nullptr;
+ }
+ DismissToBlack();
+}
+
bool Notifications::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
if (mode != Modes::Normal) {
if (!interacted && event == TouchEvents::Tap) {
interacted = true;
OnPreviewInteraction();
return true;
+ } else if (event == Pinetime::Applications::TouchEvents::SwipeRight) {
+ OnPreviewDismiss();
+ return true;
}
return false;
}
@@ -139,15 +164,9 @@ bool Notifications::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
switch (event) {
case Pinetime::Applications::TouchEvents::SwipeRight:
if (validDisplay) {
- Controllers::NotificationManager::Notification previousNotification;
auto previousMessage = notificationManager.GetPrevious(currentId);
auto nextMessage = notificationManager.GetNext(currentId);
- if (!previousMessage.valid) {
- // dismissed last message (like 5/5), need to go one message down (like 4/4)
- afterDismissNextMessageFromAbove = false; // show next message coming from below
- } else {
- afterDismissNextMessageFromAbove = true; // show next message coming from above
- }
+ afterDismissNextMessageFromAbove = previousMessage.valid;
notificationManager.Dismiss(currentId);
if (previousMessage.valid) {
currentId = previousMessage.id;
@@ -156,13 +175,7 @@ bool Notifications::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
} else {
// don't update id, won't be found be refresh and try to load latest message or no message box
}
- currentItem.reset(nullptr);
- app->SetFullRefresh(DisplayApp::FullRefreshDirections::RightAnim);
- // create black transition screen to let the notification dismiss to blackness
- lv_obj_t* blackBox = lv_obj_create(lv_scr_act(), nullptr);
- lv_obj_set_size(blackBox, LV_HOR_RES, LV_VER_RES);
- lv_obj_set_style_local_bg_color(blackBox, LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_BLACK);
- dismissingNotification = true;
+ DismissToBlack();
return true;
}
return false;
@@ -270,7 +283,7 @@ Notifications::NotificationItem::NotificationItem(const char* title,
lv_obj_t* alert_count = lv_label_create(container, nullptr);
lv_label_set_text_fmt(alert_count, "%i/%i", notifNr, notifNb);
- lv_obj_align(alert_count, NULL, LV_ALIGN_IN_TOP_RIGHT, 0, 16);
+ lv_obj_align(alert_count, nullptr, LV_ALIGN_IN_TOP_RIGHT, 0, 16);
lv_obj_t* alert_type = lv_label_create(container, nullptr);
lv_obj_set_style_local_text_color(alert_type, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, Colors::orange);
@@ -288,7 +301,7 @@ Notifications::NotificationItem::NotificationItem(const char* title,
}
lv_label_set_long_mode(alert_type, LV_LABEL_LONG_SROLL_CIRC);
lv_obj_set_width(alert_type, 180);
- lv_obj_align(alert_type, NULL, LV_ALIGN_IN_TOP_LEFT, 0, 16);
+ lv_obj_align(alert_type, nullptr, LV_ALIGN_IN_TOP_LEFT, 0, 16);
lv_obj_t* alert_subject = lv_label_create(subject_container, nullptr);
lv_label_set_long_mode(alert_subject, LV_LABEL_LONG_BREAK);
@@ -312,7 +325,7 @@ Notifications::NotificationItem::NotificationItem(const char* title,
bt_accept->user_data = this;
lv_obj_set_event_cb(bt_accept, CallEventHandler);
lv_obj_set_size(bt_accept, 76, 76);
- lv_obj_align(bt_accept, NULL, LV_ALIGN_IN_BOTTOM_LEFT, 0, 0);
+ lv_obj_align(bt_accept, nullptr, LV_ALIGN_IN_BOTTOM_LEFT, 0, 0);
label_accept = lv_label_create(bt_accept, nullptr);
lv_label_set_text_static(label_accept, Symbols::phone);
lv_obj_set_style_local_bg_color(bt_accept, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, Colors::highlight);
@@ -321,7 +334,7 @@ Notifications::NotificationItem::NotificationItem(const char* title,
bt_reject->user_data = this;
lv_obj_set_event_cb(bt_reject, CallEventHandler);
lv_obj_set_size(bt_reject, 76, 76);
- lv_obj_align(bt_reject, NULL, LV_ALIGN_IN_BOTTOM_MID, 0, 0);
+ lv_obj_align(bt_reject, nullptr, LV_ALIGN_IN_BOTTOM_MID, 0, 0);
label_reject = lv_label_create(bt_reject, nullptr);
lv_label_set_text_static(label_reject, Symbols::phoneSlash);
lv_obj_set_style_local_bg_color(bt_reject, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_RED);
@@ -330,7 +343,7 @@ Notifications::NotificationItem::NotificationItem(const char* title,
bt_mute->user_data = this;
lv_obj_set_event_cb(bt_mute, CallEventHandler);
lv_obj_set_size(bt_mute, 76, 76);
- lv_obj_align(bt_mute, NULL, LV_ALIGN_IN_BOTTOM_RIGHT, 0, 0);
+ lv_obj_align(bt_mute, nullptr, LV_ALIGN_IN_BOTTOM_RIGHT, 0, 0);
label_mute = lv_label_create(bt_mute, nullptr);
lv_label_set_text_static(label_mute, Symbols::volumMute);
lv_obj_set_style_local_bg_color(bt_mute, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, Colors::lightGray);
diff --git a/src/displayapp/screens/Notifications.h b/src/displayapp/screens/Notifications.h
index 9d843a9b..a4d2709b 100644
--- a/src/displayapp/screens/Notifications.h
+++ b/src/displayapp/screens/Notifications.h
@@ -13,6 +13,7 @@ namespace Pinetime {
namespace Controllers {
class AlertNotificationService;
}
+
namespace Applications {
namespace Screens {
@@ -29,7 +30,9 @@ namespace Pinetime {
void Refresh() override;
bool OnTouchEvent(Pinetime::Applications::TouchEvents event) override;
+ void DismissToBlack();
void OnPreviewInteraction();
+ void OnPreviewDismiss();
class NotificationItem {
public:
@@ -43,9 +46,11 @@ namespace Pinetime {
Pinetime::Controllers::AlertNotificationService& alertNotificationService,
Pinetime::Controllers::MotorController& motorController);
~NotificationItem();
+
bool IsRunning() const {
return running;
}
+
void OnCallButtonEvent(lv_obj_t*, lv_event_t event);
private:
diff --git a/src/displayapp/screens/Paddle.cpp b/src/displayapp/screens/Paddle.cpp
index 1fb25085..dc973957 100644
--- a/src/displayapp/screens/Paddle.cpp
+++ b/src/displayapp/screens/Paddle.cpp
@@ -79,11 +79,11 @@ void Paddle::Refresh() {
lv_label_set_text_fmt(points, "%04d", score);
}
-bool Paddle::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
+bool Paddle::OnTouchEvent(Pinetime::Applications::TouchEvents /*event*/) {
return true;
}
-bool Paddle::OnTouchEvent(uint16_t x, uint16_t y) {
+bool Paddle::OnTouchEvent(uint16_t /*x*/, uint16_t y) {
// sets the center paddle pos. (30px offset) with the the y_coordinate of the finger
// but clamp it such that the paddle never clips off screen
if (y < 31) {
diff --git a/src/displayapp/screens/Paddle.h b/src/displayapp/screens/Paddle.h
index 3a30eee6..d62550c4 100644
--- a/src/displayapp/screens/Paddle.h
+++ b/src/displayapp/screens/Paddle.h
@@ -8,6 +8,7 @@ namespace Pinetime {
namespace Components {
class LittleVgl;
}
+
namespace Applications {
namespace Screens {
diff --git a/src/displayapp/screens/Screen.h b/src/displayapp/screens/Screen.h
index e72a2368..4cf134d2 100644
--- a/src/displayapp/screens/Screen.h
+++ b/src/displayapp/screens/Screen.h
@@ -7,13 +7,16 @@
namespace Pinetime {
namespace Applications {
class DisplayApp;
+
namespace Screens {
template <class T> class DirtyValue {
public:
DirtyValue() = default; // Use NSDMI
+
explicit DirtyValue(T const& v) : value {v} {
} // Use MIL and const-lvalue-ref
+
bool IsUpdated() {
if (this->isUpdated) {
this->isUpdated = false;
@@ -21,10 +24,12 @@ namespace Pinetime {
}
return false;
}
+
T const& Get() {
this->isUpdated = false;
return value;
} // never expose a non-const lvalue-ref
+
DirtyValue& operator=(const T& other) {
if (this->value != other) {
this->value = other;
@@ -46,6 +51,7 @@ namespace Pinetime {
public:
explicit Screen(DisplayApp* app) : app {app} {
}
+
virtual ~Screen() = default;
static void RefreshTaskCallback(lv_task_t* task);
@@ -61,10 +67,11 @@ namespace Pinetime {
/** @return false if the event hasn't been handled by the app, true if it has been handled */
// Returning true will cancel lvgl tap
- virtual bool OnTouchEvent(TouchEvents event) {
+ virtual bool OnTouchEvent(TouchEvents /*event*/) {
return false;
}
- virtual bool OnTouchEvent(uint16_t x, uint16_t y) {
+
+ virtual bool OnTouchEvent(uint16_t /*x*/, uint16_t /*y*/) {
return false;
}
diff --git a/src/displayapp/screens/ScreenList.h b/src/displayapp/screens/ScreenList.h
index ad882948..6c9a2218 100644
--- a/src/displayapp/screens/ScreenList.h
+++ b/src/displayapp/screens/ScreenList.h
@@ -11,6 +11,7 @@ namespace Pinetime {
namespace Screens {
enum class ScreenListModes { UpDown, RightLeft, LongPress };
+
template <size_t N> class ScreenList : public Screen {
public:
ScreenList(DisplayApp* app,
diff --git a/src/displayapp/screens/Steps.h b/src/displayapp/screens/Steps.h
index f109e0f2..32ad40bd 100644
--- a/src/displayapp/screens/Steps.h
+++ b/src/displayapp/screens/Steps.h
@@ -29,7 +29,6 @@ namespace Pinetime {
uint32_t currentTripSteps = 0;
lv_obj_t* lSteps;
- lv_obj_t* lStepsIcon;
lv_obj_t* stepsArc;
lv_obj_t* resetBtn;
lv_obj_t* resetButtonLabel;
diff --git a/src/displayapp/screens/SystemInfo.cpp b/src/displayapp/screens/SystemInfo.cpp
index 01c35195..b5b17347 100644
--- a/src/displayapp/screens/SystemInfo.cpp
+++ b/src/displayapp/screens/SystemInfo.cpp
@@ -99,7 +99,7 @@ std::unique_ptr<Screen> SystemInfo::CreateScreen1() {
std::unique_ptr<Screen> SystemInfo::CreateScreen2() {
auto batteryPercent = batteryController.PercentRemaining();
- auto resetReason = [this]() {
+ const auto* resetReason = [this]() {
switch (watchdog.ResetReason()) {
case Drivers::Watchdog::ResetReasons::Watchdog:
return "wtdg";
@@ -182,7 +182,7 @@ std::unique_ptr<Screen> SystemInfo::CreateScreen3() {
lv_obj_t* label = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_recolor(label, true);
- auto& bleAddr = bleController.Address();
+ const auto& bleAddr = bleController.Address();
lv_label_set_text_fmt(label,
"#808080 BLE MAC#\n"
" %02x:%02x:%02x:%02x:%02x:%02x"
diff --git a/src/displayapp/screens/Tile.cpp b/src/displayapp/screens/Tile.cpp
index a60076ed..681f9c9f 100644
--- a/src/displayapp/screens/Tile.cpp
+++ b/src/displayapp/screens/Tile.cpp
@@ -51,8 +51,9 @@ Tile::Tile(uint8_t screenID,
uint8_t btIndex = 0;
for (uint8_t i = 0; i < 6; i++) {
- if (i == 3)
+ if (i == 3) {
btnmMap[btIndex++] = "\n";
+ }
if (applications[i].application == Apps::None) {
btnmMap[btIndex] = " ";
} else {
@@ -66,7 +67,7 @@ Tile::Tile(uint8_t screenID,
btnm1 = lv_btnmatrix_create(lv_scr_act(), nullptr);
lv_btnmatrix_set_map(btnm1, btnmMap);
lv_obj_set_size(btnm1, LV_HOR_RES - 16, LV_VER_RES - 60);
- lv_obj_align(btnm1, NULL, LV_ALIGN_CENTER, 0, 10);
+ lv_obj_align(btnm1, nullptr, LV_ALIGN_CENTER, 0, 10);
lv_obj_set_style_local_radius(btnm1, LV_BTNMATRIX_PART_BTN, LV_STATE_DEFAULT, 20);
lv_obj_set_style_local_bg_opa(btnm1, LV_BTNMATRIX_PART_BTN, LV_STATE_DEFAULT, LV_OPA_50);
@@ -102,8 +103,9 @@ void Tile::UpdateScreen() {
}
void Tile::OnValueChangedEvent(lv_obj_t* obj, uint32_t buttonId) {
- if (obj != btnm1)
+ if (obj != btnm1) {
return;
+ }
app->StartApp(apps[buttonId], DisplayApp::FullRefreshDirections::Up);
running = false;
diff --git a/src/displayapp/screens/Timer.h b/src/displayapp/screens/Timer.h
index a6b60a17..306281d7 100644
--- a/src/displayapp/screens/Timer.h
+++ b/src/displayapp/screens/Timer.h
@@ -26,7 +26,6 @@ namespace Pinetime::Applications::Screens {
void UpdateMask();
Controllers::TimerController& timerController;
- lv_obj_t* msecTime;
lv_obj_t* btnPlayPause;
lv_obj_t* txtPlayPause;
@@ -40,7 +39,7 @@ namespace Pinetime::Applications::Screens {
Widgets::Counter secondCounter = Widgets::Counter(0, 59, jetbrains_mono_76);
bool buttonPressing = false;
- int maskPosition = 0;
- TickType_t pressTime;
+ lv_coord_t maskPosition = 0;
+ TickType_t pressTime = 0;
};
}
diff --git a/src/displayapp/screens/Twos.h b/src/displayapp/screens/Twos.h
index da935724..15017581 100644
--- a/src/displayapp/screens/Twos.h
+++ b/src/displayapp/screens/Twos.h
@@ -9,6 +9,7 @@ namespace Pinetime {
bool merged = false;
unsigned int value = 0;
};
+
namespace Screens {
class Twos : public Screen {
public:
diff --git a/src/displayapp/screens/WatchFaceAnalog.cpp b/src/displayapp/screens/WatchFaceAnalog.cpp
index 5e5317ee..b36c29d3 100644
--- a/src/displayapp/screens/WatchFaceAnalog.cpp
+++ b/src/displayapp/screens/WatchFaceAnalog.cpp
@@ -61,9 +61,9 @@ WatchFaceAnalog::WatchFaceAnalog(Pinetime::Applications::DisplayApp* app,
sMinute = 99;
sSecond = 99;
- lv_obj_t* bg_clock_img = lv_img_create(lv_scr_act(), NULL);
+ lv_obj_t* bg_clock_img = lv_img_create(lv_scr_act(), nullptr);
lv_img_set_src(bg_clock_img, &bg_clock);
- lv_obj_align(bg_clock_img, NULL, LV_ALIGN_CENTER, 0, 0);
+ lv_obj_align(bg_clock_img, nullptr, LV_ALIGN_CENTER, 0, 0);
batteryIcon.Create(lv_scr_act());
lv_obj_align(batteryIcon.GetObject(), nullptr, LV_ALIGN_IN_TOP_RIGHT, 0, 0);
@@ -72,24 +72,24 @@ WatchFaceAnalog::WatchFaceAnalog(Pinetime::Applications::DisplayApp* app,
lv_label_set_text_static(plugIcon, Symbols::plug);
lv_obj_align(plugIcon, nullptr, LV_ALIGN_IN_TOP_RIGHT, 0, 0);
- notificationIcon = lv_label_create(lv_scr_act(), NULL);
+ notificationIcon = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_color(notificationIcon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_LIME);
lv_label_set_text_static(notificationIcon, NotificationIcon::GetIcon(false));
- lv_obj_align(notificationIcon, NULL, LV_ALIGN_IN_TOP_LEFT, 0, 0);
+ lv_obj_align(notificationIcon, nullptr, LV_ALIGN_IN_TOP_LEFT, 0, 0);
// Date - Day / Week day
- label_date_day = lv_label_create(lv_scr_act(), NULL);
+ label_date_day = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_color(label_date_day, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, Colors::orange);
lv_label_set_text_fmt(label_date_day, "%s\n%02i", dateTimeController.DayOfWeekShortToString(), dateTimeController.Day());
lv_label_set_align(label_date_day, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(label_date_day, NULL, LV_ALIGN_CENTER, 50, 0);
+ lv_obj_align(label_date_day, nullptr, LV_ALIGN_CENTER, 50, 0);
- minute_body = lv_line_create(lv_scr_act(), NULL);
- minute_body_trace = lv_line_create(lv_scr_act(), NULL);
- hour_body = lv_line_create(lv_scr_act(), NULL);
- hour_body_trace = lv_line_create(lv_scr_act(), NULL);
- second_body = lv_line_create(lv_scr_act(), NULL);
+ minute_body = lv_line_create(lv_scr_act(), nullptr);
+ minute_body_trace = lv_line_create(lv_scr_act(), nullptr);
+ hour_body = lv_line_create(lv_scr_act(), nullptr);
+ hour_body_trace = lv_line_create(lv_scr_act(), nullptr);
+ second_body = lv_line_create(lv_scr_act(), nullptr);
lv_style_init(&second_line_style);
lv_style_set_line_width(&second_line_style, LV_STATE_DEFAULT, 3);
diff --git a/src/displayapp/screens/WatchFaceAnalog.h b/src/displayapp/screens/WatchFaceAnalog.h
index 04d9e711..6e4e88a3 100644
--- a/src/displayapp/screens/WatchFaceAnalog.h
+++ b/src/displayapp/screens/WatchFaceAnalog.h
@@ -18,6 +18,7 @@ namespace Pinetime {
class Ble;
class NotificationManager;
}
+
namespace Applications {
namespace Screens {
diff --git a/src/displayapp/screens/WatchFaceCasioStyleG7710.cpp b/src/displayapp/screens/WatchFaceCasioStyleG7710.cpp
index bdae0d42..94b6a405 100644
--- a/src/displayapp/screens/WatchFaceCasioStyleG7710.cpp
+++ b/src/displayapp/screens/WatchFaceCasioStyleG7710.cpp
@@ -333,6 +333,7 @@ void WatchFaceCasioStyleG7710::Refresh() {
lv_obj_realign(stepIcon);
}
}
+
bool WatchFaceCasioStyleG7710::IsAvailable(Pinetime::Controllers::FS& filesystem) {
lfs_file file = {};
diff --git a/src/displayapp/screens/WatchFaceInfineat.cpp b/src/displayapp/screens/WatchFaceInfineat.cpp
index bd4e4ac8..ddf3cbcc 100644
--- a/src/displayapp/screens/WatchFaceInfineat.cpp
+++ b/src/displayapp/screens/WatchFaceInfineat.cpp
@@ -47,125 +47,40 @@ WatchFaceInfineat::WatchFaceInfineat(DisplayApp* app,
font_bebas = lv_font_load("F:/fonts/bebas.bin");
}
- // Black background covering the whole screen
- background = lv_obj_create(lv_scr_act(), nullptr);
- lv_obj_set_style_local_bg_color(background, LV_BTN_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_BLACK);
- lv_obj_set_size(background, 240, 240);
- lv_obj_align(background, lv_scr_act(), LV_ALIGN_IN_TOP_LEFT, 0, 0);
-
// Side Cover
- line0 = lv_line_create(lv_scr_act(), nullptr);
- line1 = lv_line_create(lv_scr_act(), nullptr);
- line2 = lv_line_create(lv_scr_act(), nullptr);
- line3 = lv_line_create(lv_scr_act(), nullptr);
- line4 = lv_line_create(lv_scr_act(), nullptr);
- line5 = lv_line_create(lv_scr_act(), nullptr);
- line6 = lv_line_create(lv_scr_act(), nullptr);
- line7 = lv_line_create(lv_scr_act(), nullptr);
- line8 = lv_line_create(lv_scr_act(), nullptr);
- lineBattery = lv_line_create(lv_scr_act(), nullptr);
-
- lv_style_init(&line0Style);
- lv_style_set_line_width(&line0Style, LV_STATE_DEFAULT, 18);
- lv_style_set_line_color(&line0Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines]));
- lv_obj_add_style(line0, LV_LINE_PART_MAIN, &line0Style);
- line0Points[0] = {30, 25};
- line0Points[1] = {68, -8};
- lv_line_set_points(line0, line0Points, 2);
-
- lv_style_init(&line1Style);
- lv_style_set_line_width(&line1Style, LV_STATE_DEFAULT, 15);
- lv_style_set_line_color(&line1Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 1]));
- lv_obj_add_style(line1, LV_LINE_PART_MAIN, &line1Style);
- line1Points[0] = {26, 167};
- line1Points[1] = {43, 216};
- lv_line_set_points(line1, line1Points, 2);
-
- lv_style_init(&line2Style);
- lv_style_set_line_width(&line2Style, LV_STATE_DEFAULT, 14);
- lv_style_set_line_color(&line2Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 2]));
- lv_obj_add_style(line2, LV_LINE_PART_MAIN, &line2Style);
- line2Points[0] = {27, 40};
- line2Points[1] = {27, 196};
- lv_line_set_points(line2, line2Points, 2);
-
- lv_style_init(&line3Style);
- lv_style_set_line_width(&line3Style, LV_STATE_DEFAULT, 22);
- lv_style_set_line_color(&line3Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 3]));
- lv_obj_add_style(line3, LV_LINE_PART_MAIN, &line3Style);
- line3Points[0] = {12, 182};
- line3Points[1] = {65, 249};
- lv_line_set_points(line3, line3Points, 2);
-
- lv_style_init(&line4Style);
- lv_style_set_line_width(&line4Style, LV_STATE_DEFAULT, 20);
- lv_style_set_line_color(&line4Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 4]));
- lv_obj_add_style(line4, LV_LINE_PART_MAIN, &line4Style);
- line4Points[0] = {17, 99};
- line4Points[1] = {17, 144};
- lv_line_set_points(line4, line4Points, 2);
+ static constexpr lv_point_t linePoints[nLines][2] = {{{30, 25}, {68, -8}},
+ {{26, 167}, {43, 216}},
+ {{27, 40}, {27, 196}},
+ {{12, 182}, {65, 249}},
+ {{17, 99}, {17, 144}},
+ {{14, 81}, {40, 127}},
+ {{14, 163}, {40, 118}},
+ {{-20, 124}, {25, -11}},
+ {{-29, 89}, {27, 254}}};
- lv_style_init(&line5Style);
- lv_style_set_line_width(&line5Style, LV_STATE_DEFAULT, 18);
- lv_style_set_line_color(&line5Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 5]));
- lv_obj_add_style(line5, LV_LINE_PART_MAIN, &line5Style);
- line5Points[0] = {14, 81};
- line5Points[1] = {40, 127};
- lv_line_set_points(line5, line5Points, 2);
+ static constexpr lv_style_int_t lineWidths[nLines] = {18, 15, 14, 22, 20, 18, 18, 52, 48};
- lv_style_init(&line6Style);
- lv_style_set_line_width(&line6Style, LV_STATE_DEFAULT, 18);
- lv_style_set_line_color(&line6Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 6]));
- lv_obj_add_style(line6, LV_LINE_PART_MAIN, &line6Style);
- line6Points[0] = {14, 163};
- line6Points[1] = {40, 118};
- lv_line_set_points(line6, line6Points, 2);
-
- lv_style_init(&line7Style);
- lv_style_set_line_width(&line7Style, LV_STATE_DEFAULT, 52);
- lv_style_set_line_color(&line7Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 7]));
- lv_obj_add_style(line7, LV_LINE_PART_MAIN, &line7Style);
- line7Points[0] = {-20, 124};
- line7Points[1] = {25, -11};
- lv_line_set_points(line7, line7Points, 2);
-
- lv_style_init(&line8Style);
- lv_style_set_line_width(&line8Style, LV_STATE_DEFAULT, 48);
- lv_style_set_line_color(&line8Style,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 8]));
- lv_obj_add_style(line8, LV_LINE_PART_MAIN, &line8Style);
- line8Points[0] = {-29, 89};
- line8Points[1] = {27, 254};
- lv_line_set_points(line8, line8Points, 2);
+ for (int i = 0; i < nLines; i++) {
+ lines[i] = lv_line_create(lv_scr_act(), nullptr);
+ lv_obj_set_style_local_line_width(lines[i], LV_LINE_PART_MAIN, LV_STATE_DEFAULT, lineWidths[i]);
+ lv_obj_set_style_local_line_color(lines[i],
+ LV_LINE_PART_MAIN,
+ LV_STATE_DEFAULT,
+ lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + i]));
+ lv_line_set_points(lines[i], linePoints[i], 2);
+ }
logoPine = lv_img_create(lv_scr_act(), nullptr);
lv_img_set_src(logoPine, "F:/images/pine_small.bin");
lv_obj_set_pos(logoPine, 15, 106);
- lv_style_init(&lineBatteryStyle);
- lv_style_set_line_width(&lineBatteryStyle, LV_STATE_DEFAULT, 24);
- lv_style_set_line_color(&lineBatteryStyle,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 4]));
- lv_style_set_line_opa(&lineBatteryStyle, LV_STATE_DEFAULT, 190);
- lv_obj_add_style(lineBattery, LV_LINE_PART_MAIN, &lineBatteryStyle);
+ lineBattery = lv_line_create(lv_scr_act(), nullptr);
+ lv_obj_set_style_local_line_width(lineBattery, LV_LINE_PART_MAIN, LV_STATE_DEFAULT, 24);
+ lv_obj_set_style_local_line_color(lineBattery,
+ LV_LINE_PART_MAIN,
+ LV_STATE_DEFAULT,
+ lv_color_hex(infineatColors.orange[settingsController.GetInfineatColorIndex() * nLines + 4]));
+ lv_obj_set_style_local_line_opa(lineBattery, LV_LINE_PART_MAIN, LV_STATE_DEFAULT, 190);
lineBatteryPoints[0] = {27, 105};
lineBatteryPoints[1] = {27, 106};
lv_line_set_points(lineBattery, lineBatteryPoints, 2);
@@ -182,55 +97,30 @@ WatchFaceInfineat::WatchFaceInfineat(DisplayApp* app,
if (!settingsController.GetInfineatShowSideCover()) {
ToggleBatteryIndicatorColor(false);
- lv_obj_set_hidden(line0, true);
- lv_obj_set_hidden(line1, true);
- lv_obj_set_hidden(line2, true);
- lv_obj_set_hidden(line3, true);
- lv_obj_set_hidden(line4, true);
- lv_obj_set_hidden(line5, true);
- lv_obj_set_hidden(line6, true);
- lv_obj_set_hidden(line7, true);
- lv_obj_set_hidden(line8, true);
+ for (auto& line : lines) {
+ lv_obj_set_hidden(line, true);
+ }
}
timeContainer = lv_obj_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_bg_opa(timeContainer, LV_BTN_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
- if (font_bebas != nullptr) {
- lv_obj_set_size(timeContainer, 185, 185);
- lv_obj_align(timeContainer, lv_scr_act(), LV_ALIGN_CENTER, 0, -10);
- } else {
- lv_obj_set_size(timeContainer, 110, 145);
- lv_obj_align(timeContainer, lv_scr_act(), LV_ALIGN_CENTER, 0, 0);
- }
+ lv_obj_set_size(timeContainer, 185, 185);
+ lv_obj_align(timeContainer, lv_scr_act(), LV_ALIGN_CENTER, 0, -10);
labelHour = lv_label_create(lv_scr_act(), nullptr);
- lv_obj_set_style_local_text_font(labelHour, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &jetbrains_mono_extrabold_compressed);
- lv_label_set_text(labelHour, "01");
- if (font_bebas != nullptr) {
- lv_obj_set_style_local_text_font(labelHour, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_bebas);
- lv_obj_align(labelHour, timeContainer, LV_ALIGN_IN_TOP_MID, 0, 0);
- } else {
- lv_obj_set_style_local_text_font(labelHour, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &jetbrains_mono_extrabold_compressed);
- lv_obj_align(labelHour, timeContainer, LV_ALIGN_IN_TOP_MID, 0, 5);
- }
+ lv_label_set_text_static(labelHour, "01");
+ lv_obj_set_style_local_text_font(labelHour, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_bebas);
+ lv_obj_align(labelHour, timeContainer, LV_ALIGN_IN_TOP_MID, 0, 0);
labelMinutes = lv_label_create(lv_scr_act(), nullptr);
- if (font_bebas != nullptr) {
- lv_obj_set_style_local_text_font(labelMinutes, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_bebas);
- } else {
- lv_obj_set_style_local_text_font(labelMinutes, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &jetbrains_mono_extrabold_compressed);
- }
- lv_label_set_text(labelMinutes, "00");
+ lv_obj_set_style_local_text_font(labelMinutes, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_bebas);
+ lv_label_set_text_static(labelMinutes, "00");
lv_obj_align(labelMinutes, timeContainer, LV_ALIGN_IN_BOTTOM_MID, 0, 0);
labelTimeAmPm = lv_label_create(lv_scr_act(), nullptr);
- if (font_teko != nullptr) {
- lv_obj_set_style_local_text_font(labelTimeAmPm, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_teko);
- } else {
- lv_obj_set_style_local_text_font(labelTimeAmPm, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &jetbrains_mono_bold_20);
- }
+ lv_obj_set_style_local_text_font(labelTimeAmPm, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_teko);
- lv_label_set_text(labelTimeAmPm, "");
+ lv_label_set_text_static(labelTimeAmPm, "");
lv_obj_align(labelTimeAmPm, timeContainer, LV_ALIGN_OUT_RIGHT_TOP, 0, 15);
dateContainer = lv_obj_create(lv_scr_act(), nullptr);
@@ -240,32 +130,24 @@ WatchFaceInfineat::WatchFaceInfineat(DisplayApp* app,
labelDate = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_color(labelDate, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x999999));
- if (font_teko != nullptr) {
- lv_obj_set_style_local_text_font(labelDate, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_teko);
- } else {
- lv_obj_set_style_local_text_font(labelDate, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &jetbrains_mono_bold_20);
- }
+ lv_obj_set_style_local_text_font(labelDate, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_teko);
lv_obj_align(labelDate, dateContainer, LV_ALIGN_IN_TOP_MID, 0, 0);
- lv_label_set_text(labelDate, "Mon 01");
+ lv_label_set_text_static(labelDate, "Mon 01");
bleIcon = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_color(bleIcon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x999999));
- lv_label_set_text(bleIcon, Symbols::bluetooth);
+ lv_label_set_text_static(bleIcon, Symbols::bluetooth);
lv_obj_align(bleIcon, dateContainer, LV_ALIGN_OUT_BOTTOM_MID, 0, 0);
stepValue = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_color(stepValue, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x999999));
- if (font_teko != nullptr) {
- lv_obj_set_style_local_text_font(stepValue, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_teko);
- } else {
- lv_obj_set_style_local_text_font(stepValue, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, &jetbrains_mono_bold_20);
- }
+ lv_obj_set_style_local_text_font(stepValue, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font_teko);
lv_obj_align(stepValue, lv_scr_act(), LV_ALIGN_IN_BOTTOM_RIGHT, 10, 0);
- lv_label_set_text(stepValue, "0");
+ lv_label_set_text_static(stepValue, "0");
stepIcon = lv_label_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_text_color(stepIcon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, lv_color_hex(0x999999));
- lv_label_set_text(stepIcon, Symbols::shoe);
+ lv_label_set_text_static(stepIcon, Symbols::shoe);
lv_obj_align(stepIcon, stepValue, LV_ALIGN_OUT_LEFT_MID, -5, 0);
// Setting buttons
@@ -330,17 +212,6 @@ WatchFaceInfineat::WatchFaceInfineat(DisplayApp* app,
WatchFaceInfineat::~WatchFaceInfineat() {
lv_task_del(taskRefresh);
- lv_style_reset(&line0Style);
- lv_style_reset(&line1Style);
- lv_style_reset(&line2Style);
- lv_style_reset(&line3Style);
- lv_style_reset(&line4Style);
- lv_style_reset(&line5Style);
- lv_style_reset(&line6Style);
- lv_style_reset(&line7Style);
- lv_style_reset(&line8Style);
- lv_style_reset(&lineBatteryStyle);
-
if (font_bebas != nullptr) {
lv_font_free(font_bebas);
}
@@ -398,15 +269,9 @@ void WatchFaceInfineat::UpdateSelected(lv_obj_t* object, lv_event_t event) {
if (object == btnToggleCover) {
settingsController.SetInfineatShowSideCover(!showSideCover);
ToggleBatteryIndicatorColor(!showSideCover);
- lv_obj_set_hidden(line0, showSideCover);
- lv_obj_set_hidden(line1, showSideCover);
- lv_obj_set_hidden(line2, showSideCover);
- lv_obj_set_hidden(line3, showSideCover);
- lv_obj_set_hidden(line4, showSideCover);
- lv_obj_set_hidden(line5, showSideCover);
- lv_obj_set_hidden(line6, showSideCover);
- lv_obj_set_hidden(line7, showSideCover);
- lv_obj_set_hidden(line8, showSideCover);
+ for (auto& line : lines) {
+ lv_obj_set_hidden(line, showSideCover);
+ }
lv_obj_set_hidden(btnNextColor, showSideCover);
lv_obj_set_hidden(btnPrevColor, showSideCover);
const char* labelToggle = showSideCover ? "OFF" : "ON";
@@ -423,42 +288,12 @@ void WatchFaceInfineat::UpdateSelected(lv_obj_t* object, lv_event_t event) {
settingsController.SetInfineatColorIndex(colorIndex);
}
if (object == btnNextColor || object == btnPrevColor) {
- lv_obj_set_style_local_line_color(line0,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 0]));
- lv_obj_set_style_local_line_color(line1,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 1]));
- lv_obj_set_style_local_line_color(line2,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 2]));
- lv_obj_set_style_local_line_color(line3,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 3]));
- lv_obj_set_style_local_line_color(line4,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 4]));
- lv_obj_set_style_local_line_color(line5,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 5]));
- lv_obj_set_style_local_line_color(line6,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 6]));
- lv_obj_set_style_local_line_color(line7,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 7]));
- lv_obj_set_style_local_line_color(line8,
- LV_LINE_PART_MAIN,
- LV_STATE_DEFAULT,
- lv_color_hex(infineatColors.orange[colorIndex * nLines + 8]));
+ for (int i = 0; i < nLines; i++) {
+ lv_obj_set_style_local_line_color(lines[i],
+ LV_LINE_PART_MAIN,
+ LV_STATE_DEFAULT,
+ lv_color_hex(infineatColors.orange[colorIndex * nLines + i]));
+ }
lv_obj_set_style_local_line_color(lineBattery,
LV_LINE_PART_MAIN,
LV_STATE_DEFAULT,
@@ -547,17 +382,13 @@ void WatchFaceInfineat::Refresh() {
batteryPercentRemaining = batteryController.PercentRemaining();
isCharging = batteryController.IsCharging();
- // We store if battery and charging are updated before calling Get(),
- // since Get() sets isUpdated to false.
- bool isBatteryUpdated = batteryPercentRemaining.IsUpdated();
- bool isChargingUpdated = isCharging.IsUpdated();
- if (isCharging.Get()) { // Charging battery animation
+ if (batteryController.IsCharging()) { // Charging battery animation
chargingBatteryPercent += 1;
if (chargingBatteryPercent > 100) {
chargingBatteryPercent = batteryPercentRemaining.Get();
}
SetBatteryLevel(chargingBatteryPercent);
- } else if (isChargingUpdated || isBatteryUpdated) {
+ } else if (isCharging.IsUpdated() || batteryPercentRemaining.IsUpdated()) {
chargingBatteryPercent = batteryPercentRemaining.Get();
SetBatteryLevel(chargingBatteryPercent);
}
@@ -565,7 +396,7 @@ void WatchFaceInfineat::Refresh() {
bleState = bleController.IsConnected();
bleRadioEnabled = bleController.IsRadioEnabled();
if (bleState.IsUpdated()) {
- lv_label_set_text(bleIcon, BleIcon::GetIcon(bleState.Get()));
+ lv_label_set_text_static(bleIcon, BleIcon::GetIcon(bleState.Get()));
lv_obj_align(bleIcon, dateContainer, LV_ALIGN_OUT_BOTTOM_MID, 0, 3);
}
diff --git a/src/displayapp/screens/WatchFaceInfineat.h b/src/displayapp/screens/WatchFaceInfineat.h
index 6c3c30ba..dfa0b38b 100644
--- a/src/displayapp/screens/WatchFaceInfineat.h
+++ b/src/displayapp/screens/WatchFaceInfineat.h
@@ -60,40 +60,9 @@ namespace Pinetime {
DirtyValue<uint32_t> stepCount {};
DirtyValue<bool> notificationState {};
- lv_obj_t* background;
-
// Lines making up the side cover
- lv_obj_t* line0;
- lv_obj_t* line1;
- lv_obj_t* line2;
- lv_obj_t* line3;
- lv_obj_t* line4;
- lv_obj_t* line5;
- lv_obj_t* line6;
- lv_obj_t* line7;
- lv_obj_t* line8;
lv_obj_t* lineBattery;
- lv_style_t line0Style;
- lv_style_t line1Style;
- lv_style_t line2Style;
- lv_style_t line3Style;
- lv_style_t line4Style;
- lv_style_t line5Style;
- lv_style_t line6Style;
- lv_style_t line7Style;
- lv_style_t line8Style;
- lv_style_t lineBatteryStyle;
-
- lv_point_t line0Points[2];
- lv_point_t line1Points[2];
- lv_point_t line2Points[2];
- lv_point_t line3Points[2];
- lv_point_t line4Points[2];
- lv_point_t line5Points[2];
- lv_point_t line6Points[2];
- lv_point_t line7Points[2];
- lv_point_t line8Points[2];
lv_point_t lineBatteryPoints[2];
lv_obj_t* logoPine;
@@ -118,6 +87,9 @@ namespace Pinetime {
static constexpr int nLines = 9;
static constexpr int nColors = 7; // must match number of colors in InfineatColors
+
+ lv_obj_t* lines[nLines];
+
struct InfineatColors {
int orange[nLines] = {0xfd872b, 0xdb3316, 0x6f1000, 0xfd7a0a, 0xffffff, 0xffffff, 0xffffff, 0xe85102, 0xea1c00};
int blue[nLines] = {0xe7f8ff, 0x2232d0, 0x182a8b, 0xe7f8ff, 0xffffff, 0xffffff, 0xffffff, 0x5991ff, 0x1636ff};
diff --git a/src/displayapp/screens/WatchFacePineTimeStyle.h b/src/displayapp/screens/WatchFacePineTimeStyle.h
index 3085a1ae..b2cb0736 100644
--- a/src/displayapp/screens/WatchFacePineTimeStyle.h
+++ b/src/displayapp/screens/WatchFacePineTimeStyle.h
@@ -5,10 +5,10 @@
#include <cstdint>
#include <memory>
#include "displayapp/screens/Screen.h"
+#include "displayapp/screens/BatteryIcon.h"
#include "displayapp/Colors.h"
#include "components/datetime/DateTimeController.h"
#include "components/ble/BleController.h"
-#include <displayapp/screens/BatteryIcon.h>
namespace Pinetime {
namespace Controllers {
diff --git a/src/displayapp/screens/WatchFaceTerminal.cpp b/src/displayapp/screens/WatchFaceTerminal.cpp
index 92189737..d04cc517 100644
--- a/src/displayapp/screens/WatchFaceTerminal.cpp
+++ b/src/displayapp/screens/WatchFaceTerminal.cpp
@@ -30,8 +30,6 @@ WatchFaceTerminal::WatchFaceTerminal(DisplayApp* app,
settingsController {settingsController},
heartRateController {heartRateController},
motionController {motionController} {
- settingsController.SetClockFace(3);
-
batteryValue = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_recolor(batteryValue, true);
lv_obj_align(batteryValue, lv_scr_act(), LV_ALIGN_IN_LEFT_MID, 0, -20);
diff --git a/src/displayapp/screens/Weather.cpp b/src/displayapp/screens/Weather.cpp
index 1d0a83bd..ff067db8 100644
--- a/src/displayapp/screens/Weather.cpp
+++ b/src/displayapp/screens/Weather.cpp
@@ -27,7 +27,6 @@ using namespace Pinetime::Applications::Screens;
Weather::Weather(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::WeatherService& weather)
: Screen(app),
- dateTimeController {dateTimeController},
weatherService(weather),
screens {app,
0,
diff --git a/src/displayapp/screens/Weather.h b/src/displayapp/screens/Weather.h
index 34f95fce..21b05bd8 100644
--- a/src/displayapp/screens/Weather.h
+++ b/src/displayapp/screens/Weather.h
@@ -25,7 +25,6 @@ namespace Pinetime {
private:
bool running = true;
- Pinetime::Controllers::DateTime& dateTimeController;
Controllers::WeatherService& weatherService;
ScreenList<5> screens;
diff --git a/src/displayapp/screens/settings/SettingBluetooth.cpp b/src/displayapp/screens/settings/SettingBluetooth.cpp
index c66be3e9..fd07be88 100644
--- a/src/displayapp/screens/settings/SettingBluetooth.cpp
+++ b/src/displayapp/screens/settings/SettingBluetooth.cpp
@@ -9,84 +9,52 @@
using namespace Pinetime::Applications::Screens;
namespace {
- void OnBluetoothDisabledEvent(lv_obj_t* obj, lv_event_t event) {
- auto* screen = static_cast<SettingBluetooth*>(obj->user_data);
- screen->OnBluetoothDisabled(obj, event);
- }
+ struct Option {
+ const char* name;
+ bool radioEnabled;
+ };
- void OnBluetoothEnabledEvent(lv_obj_t* obj, lv_event_t event) {
- auto* screen = static_cast<SettingBluetooth*>(obj->user_data);
- screen->OnBluetoothEnabled(obj, event);
- }
+ constexpr std::array<Option, 2> options = {{
+ {"Enabled", true},
+ {"Disabled", false},
+ }};
+
+ std::array<CheckboxList::Item, CheckboxList::MaxItems> CreateOptionArray() {
+ std::array<Pinetime::Applications::Screens::CheckboxList::Item, CheckboxList::MaxItems> optionArray;
+ for (size_t i = 0; i < CheckboxList::MaxItems; i++) {
+ if (i >= options.size()) {
+ optionArray[i].name = "";
+ optionArray[i].enabled = false;
+ } else {
+ optionArray[i].name = options[i].name;
+ optionArray[i].enabled = true;
+ }
+ }
+ return optionArray;
+ };
}
SettingBluetooth::SettingBluetooth(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Settings& settingsController)
- : Screen(app), settingsController {settingsController} {
-
- lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
-
- lv_obj_set_style_local_bg_opa(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
- lv_obj_set_style_local_pad_all(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 10);
- lv_obj_set_style_local_pad_inner(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 5);
- lv_obj_set_style_local_border_width(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 0);
-
- lv_obj_set_pos(container1, 10, 60);
- lv_obj_set_width(container1, LV_HOR_RES - 20);
- lv_obj_set_height(container1, LV_VER_RES - 50);
- lv_cont_set_layout(container1, LV_LAYOUT_COLUMN_LEFT);
-
- lv_obj_t* title = lv_label_create(lv_scr_act(), nullptr);
- lv_label_set_text_static(title, "Bluetooth");
- lv_label_set_align(title, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(title, lv_scr_act(), LV_ALIGN_IN_TOP_MID, 15, 15);
-
- lv_obj_t* icon = lv_label_create(lv_scr_act(), nullptr);
- lv_obj_set_style_local_text_color(icon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_ORANGE);
- lv_label_set_text_static(icon, Symbols::bluetooth);
- lv_label_set_align(icon, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(icon, title, LV_ALIGN_OUT_LEFT_MID, -10, 0);
-
- cbEnabled = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text(cbEnabled, " Enabled");
- cbEnabled->user_data = this;
- lv_obj_set_event_cb(cbEnabled, OnBluetoothEnabledEvent);
- SetRadioButtonStyle(cbEnabled);
-
- cbDisabled = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text(cbDisabled, " Disabled");
- cbDisabled->user_data = this;
- lv_obj_set_event_cb(cbDisabled, OnBluetoothDisabledEvent);
- SetRadioButtonStyle(cbDisabled);
-
- if (settingsController.GetBleRadioEnabled()) {
- lv_checkbox_set_checked(cbEnabled, true);
- priorMode = true;
- } else {
- lv_checkbox_set_checked(cbDisabled, true);
- priorMode = false;
- }
+ : Screen(app),
+ checkboxList(
+ 0,
+ 1,
+ app,
+ "Bluetooth",
+ Symbols::bluetooth,
+ settingsController.GetBleRadioEnabled() ? 0 : 1,
+ [&settings = settingsController](uint32_t index) {
+ const bool priorMode = settings.GetBleRadioEnabled();
+ const bool newMode = options[index].radioEnabled;
+ if (newMode != priorMode) {
+ settings.SetBleRadioEnabled(newMode);
+ }
+ },
+ CreateOptionArray()) {
}
SettingBluetooth::~SettingBluetooth() {
lv_obj_clean(lv_scr_act());
- // Do not call SaveSettings - see src/components/settings/Settings.h
- if (priorMode != settingsController.GetBleRadioEnabled()) {
- app->PushMessage(Pinetime::Applications::Display::Messages::BleRadioEnableToggle);
- }
-}
-
-void SettingBluetooth::OnBluetoothDisabled(lv_obj_t* object, lv_event_t event) {
- if (event == LV_EVENT_VALUE_CHANGED) {
- lv_checkbox_set_checked(cbEnabled, false);
- lv_checkbox_set_checked(cbDisabled, true);
- settingsController.SetBleRadioEnabled(false);
- }
-}
-
-void SettingBluetooth::OnBluetoothEnabled(lv_obj_t* object, lv_event_t event) {
- if (event == LV_EVENT_VALUE_CHANGED) {
- lv_checkbox_set_checked(cbEnabled, true);
- lv_checkbox_set_checked(cbDisabled, false);
- settingsController.SetBleRadioEnabled(true);
- }
+ // Pushing the message in the OnValueChanged function causes a freeze?
+ app->PushMessage(Pinetime::Applications::Display::Messages::BleRadioEnableToggle);
}
diff --git a/src/displayapp/screens/settings/SettingBluetooth.h b/src/displayapp/screens/settings/SettingBluetooth.h
index 12bb459a..611a0d5c 100644
--- a/src/displayapp/screens/settings/SettingBluetooth.h
+++ b/src/displayapp/screens/settings/SettingBluetooth.h
@@ -6,6 +6,7 @@
#include "components/settings/Settings.h"
#include "displayapp/screens/Screen.h"
+#include "displayapp/screens/CheckboxList.h"
namespace Pinetime {
@@ -17,14 +18,8 @@ namespace Pinetime {
SettingBluetooth(DisplayApp* app, Pinetime::Controllers::Settings& settingsController);
~SettingBluetooth() override;
- void OnBluetoothEnabled(lv_obj_t* object, lv_event_t event);
- void OnBluetoothDisabled(lv_obj_t* object, lv_event_t event);
-
private:
- Controllers::Settings& settingsController;
- lv_obj_t* cbEnabled;
- lv_obj_t* cbDisabled;
- bool priorMode;
+ CheckboxList checkboxList;
};
}
}
diff --git a/src/displayapp/screens/settings/SettingChimes.cpp b/src/displayapp/screens/settings/SettingChimes.cpp
index 7f519f75..6e12fb88 100644
--- a/src/displayapp/screens/settings/SettingChimes.cpp
+++ b/src/displayapp/screens/settings/SettingChimes.cpp
@@ -4,70 +4,62 @@
#include "displayapp/screens/Styles.h"
#include "displayapp/screens/Screen.h"
#include "displayapp/screens/Symbols.h"
+#include <array>
using namespace Pinetime::Applications::Screens;
namespace {
- void event_handler(lv_obj_t* obj, lv_event_t event) {
- auto* screen = static_cast<SettingChimes*>(obj->user_data);
- screen->UpdateSelected(obj, event);
- }
-}
-
-constexpr std::array<SettingChimes::Option, 3> SettingChimes::options;
-
-SettingChimes::SettingChimes(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Settings& settingsController)
- : Screen(app), settingsController {settingsController} {
-
- lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
+ struct Option {
+ Pinetime::Controllers::Settings::ChimesOption chimesOption;
+ const char* name;
+ };
- lv_obj_set_style_local_bg_opa(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
- lv_obj_set_style_local_pad_all(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 10);
- lv_obj_set_style_local_pad_inner(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 5);
- lv_obj_set_style_local_border_width(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 0);
+ constexpr std::array<Option, 3> options = {{
+ {Pinetime::Controllers::Settings::ChimesOption::None, "Off"},
+ {Pinetime::Controllers::Settings::ChimesOption::Hours, "Every hour"},
+ {Pinetime::Controllers::Settings::ChimesOption::HalfHours, "Every 30 mins"},
+ }};
- lv_obj_set_pos(container1, 10, 60);
- lv_obj_set_width(container1, LV_HOR_RES - 20);
- lv_obj_set_height(container1, LV_VER_RES - 50);
- lv_cont_set_layout(container1, LV_LAYOUT_COLUMN_LEFT);
-
- lv_obj_t* title = lv_label_create(lv_scr_act(), nullptr);
- lv_label_set_text_static(title, "Chimes");
- lv_label_set_align(title, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(title, lv_scr_act(), LV_ALIGN_IN_TOP_MID, 10, 15);
-
- lv_obj_t* icon = lv_label_create(lv_scr_act(), nullptr);
- lv_obj_set_style_local_text_color(icon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_ORANGE);
- lv_label_set_text_static(icon, Symbols::clock);
- lv_label_set_align(icon, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(icon, title, LV_ALIGN_OUT_LEFT_MID, -10, 0);
+ std::array<CheckboxList::Item, CheckboxList::MaxItems> CreateOptionArray() {
+ std::array<Pinetime::Applications::Screens::CheckboxList::Item, CheckboxList::MaxItems> optionArray;
+ for (size_t i = 0; i < CheckboxList::MaxItems; i++) {
+ if (i >= options.size()) {
+ optionArray[i].name = "";
+ optionArray[i].enabled = false;
+ } else {
+ optionArray[i].name = options[i].name;
+ optionArray[i].enabled = true;
+ }
+ }
+ return optionArray;
+ }
- for (unsigned int i = 0; i < options.size(); i++) {
- cbOption[i] = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text(cbOption[i], options[i].name);
- if (settingsController.GetChimeOption() == options[i].chimesOption) {
- lv_checkbox_set_checked(cbOption[i], true);
+ uint32_t GetDefaultOption(Pinetime::Controllers::Settings::ChimesOption currentOption) {
+ for (size_t i = 0; i < options.size(); i++) {
+ if (options[i].chimesOption == currentOption) {
+ return i;
+ }
}
- cbOption[i]->user_data = this;
- lv_obj_set_event_cb(cbOption[i], event_handler);
- SetRadioButtonStyle(cbOption[i]);
+ return 0;
}
}
-SettingChimes::~SettingChimes() {
- lv_obj_clean(lv_scr_act());
- settingsController.SaveSettings();
+SettingChimes::SettingChimes(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Settings& settingsController)
+ : Screen(app),
+ checkboxList(
+ 0,
+ 1,
+ app,
+ "Chimes",
+ Symbols::clock,
+ GetDefaultOption(settingsController.GetChimeOption()),
+ [&settings = settingsController](uint32_t index) {
+ settings.SetChimeOption(options[index].chimesOption);
+ settings.SaveSettings();
+ },
+ CreateOptionArray()) {
}
-void SettingChimes::UpdateSelected(lv_obj_t* object, lv_event_t event) {
- if (event == LV_EVENT_VALUE_CHANGED) {
- for (uint8_t i = 0; i < options.size(); i++) {
- if (object == cbOption[i]) {
- lv_checkbox_set_checked(cbOption[i], true);
- settingsController.SetChimeOption(options[i].chimesOption);
- } else {
- lv_checkbox_set_checked(cbOption[i], false);
- }
- }
- }
+SettingChimes::~SettingChimes() {
+ lv_obj_clean(lv_scr_act());
}
diff --git a/src/displayapp/screens/settings/SettingChimes.h b/src/displayapp/screens/settings/SettingChimes.h
index e48432c6..a306e81d 100644
--- a/src/displayapp/screens/settings/SettingChimes.h
+++ b/src/displayapp/screens/settings/SettingChimes.h
@@ -2,9 +2,10 @@
#include <cstdint>
#include <lvgl/lvgl.h>
+
#include "components/settings/Settings.h"
#include "displayapp/screens/Screen.h"
-#include <array>
+#include "displayapp/screens/CheckboxList.h"
namespace Pinetime {
@@ -19,19 +20,7 @@ namespace Pinetime {
void UpdateSelected(lv_obj_t* object, lv_event_t event);
private:
- struct Option {
- Controllers::Settings::ChimesOption chimesOption;
- const char* name;
- };
- static constexpr std::array<Option, 3> options = {{
- {Controllers::Settings::ChimesOption::None, " Off"},
- {Controllers::Settings::ChimesOption::Hours, " Every hour"},
- {Controllers::Settings::ChimesOption::HalfHours, " Every 30 mins"}
- }};
-
- std::array<lv_obj_t*, options.size()> cbOption;
-
- Controllers::Settings& settingsController;
+ CheckboxList checkboxList;
};
}
}
diff --git a/src/displayapp/screens/settings/SettingSetDate.cpp b/src/displayapp/screens/settings/SettingSetDate.cpp
index 421aef02..c58f6fca 100644
--- a/src/displayapp/screens/settings/SettingSetDate.cpp
+++ b/src/displayapp/screens/settings/SettingSetDate.cpp
@@ -1,4 +1,5 @@
#include "displayapp/screens/settings/SettingSetDate.h"
+#include "displayapp/screens/settings/SettingSetDateTime.h"
#include <lvgl/lvgl.h>
#include <hal/nrf_rtc.h>
#include <nrf_log.h>
@@ -44,8 +45,11 @@ namespace {
}
}
-SettingSetDate::SettingSetDate(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::DateTime& dateTimeController)
- : Screen(app), dateTimeController {dateTimeController} {
+SettingSetDate::SettingSetDate(Pinetime::Applications::DisplayApp* app,
+ Pinetime::Controllers::DateTime& dateTimeController,
+ Pinetime::Applications::Screens::SettingSetDateTime& settingSetDateTime)
+ : Screen(app), dateTimeController {dateTimeController}, settingSetDateTime {settingSetDateTime} {
+
lv_obj_t* title = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_text_static(title, "Set current date");
lv_label_set_align(title, LV_LABEL_ALIGN_CENTER);
@@ -82,8 +86,6 @@ SettingSetDate::SettingSetDate(Pinetime::Applications::DisplayApp* app, Pinetime
lblSetTime = lv_label_create(btnSetTime, nullptr);
lv_label_set_text_static(lblSetTime, "Set");
lv_obj_set_event_cb(btnSetTime, event_handler);
- lv_btn_set_state(btnSetTime, LV_BTN_STATE_DISABLED);
- lv_obj_set_state(lblSetTime, LV_STATE_DISABLED);
}
SettingSetDate::~SettingSetDate() {
@@ -98,18 +100,14 @@ void SettingSetDate::HandleButtonPress() {
dateTimeController.SetTime(yearValue,
monthValue,
dayValue,
- 0,
dateTimeController.Hours(),
dateTimeController.Minutes(),
dateTimeController.Seconds(),
nrf_rtc_counter_get(portNRF_RTC_REG));
- lv_btn_set_state(btnSetTime, LV_BTN_STATE_DISABLED);
- lv_obj_set_state(lblSetTime, LV_STATE_DISABLED);
+ settingSetDateTime.Advance();
}
void SettingSetDate::CheckDay() {
const int maxDay = MaximumDayOfMonth(monthCounter.GetValue(), yearCounter.GetValue());
dayCounter.SetMax(maxDay);
- lv_btn_set_state(btnSetTime, LV_BTN_STATE_RELEASED);
- lv_obj_set_state(lblSetTime, LV_STATE_DEFAULT);
}
diff --git a/src/displayapp/screens/settings/SettingSetDate.h b/src/displayapp/screens/settings/SettingSetDate.h
index a0ffc683..dfb0e0d2 100644
--- a/src/displayapp/screens/settings/SettingSetDate.h
+++ b/src/displayapp/screens/settings/SettingSetDate.h
@@ -5,13 +5,17 @@
#include "components/datetime/DateTimeController.h"
#include "displayapp/screens/Screen.h"
#include "displayapp/widgets/Counter.h"
+#include "displayapp/widgets/DotIndicator.h"
+#include "displayapp/screens/settings/SettingSetDateTime.h"
namespace Pinetime {
namespace Applications {
namespace Screens {
class SettingSetDate : public Screen {
public:
- SettingSetDate(DisplayApp* app, Pinetime::Controllers::DateTime& dateTimeController);
+ SettingSetDate(DisplayApp* app,
+ Pinetime::Controllers::DateTime& dateTimeController,
+ Pinetime::Applications::Screens::SettingSetDateTime& settingSetDateTime);
~SettingSetDate() override;
void HandleButtonPress();
@@ -19,6 +23,7 @@ namespace Pinetime {
private:
Controllers::DateTime& dateTimeController;
+ Pinetime::Applications::Screens::SettingSetDateTime& settingSetDateTime;
lv_obj_t* btnSetTime;
lv_obj_t* lblSetTime;
diff --git a/src/displayapp/screens/settings/SettingSetDateTime.cpp b/src/displayapp/screens/settings/SettingSetDateTime.cpp
new file mode 100644
index 00000000..905a76ab
--- /dev/null
+++ b/src/displayapp/screens/settings/SettingSetDateTime.cpp
@@ -0,0 +1,54 @@
+#include "displayapp/screens/settings/SettingSetDateTime.h"
+#include "displayapp/screens/settings/SettingSetDate.h"
+#include "displayapp/screens/settings/SettingSetTime.h"
+#include "displayapp/DisplayApp.h"
+#include "displayapp/screens/ScreenList.h"
+#include "components/settings/Settings.h"
+#include "displayapp/widgets/DotIndicator.h"
+
+using namespace Pinetime::Applications::Screens;
+
+bool SettingSetDateTime::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
+ return screens.OnTouchEvent(event);
+}
+
+SettingSetDateTime::SettingSetDateTime(Pinetime::Applications::DisplayApp* app,
+ Pinetime::Controllers::DateTime& dateTimeController,
+ Pinetime::Controllers::Settings& settingsController)
+ : Screen(app),
+ dateTimeController {dateTimeController},
+ settingsController {settingsController},
+ screens {app,
+ 0,
+ {[this]() -> std::unique_ptr<Screen> {
+ return screenSetDate();
+ },
+ [this]() -> std::unique_ptr<Screen> {
+ return screenSetTime();
+ }},
+ Screens::ScreenListModes::UpDown} {
+}
+
+std::unique_ptr<Screen> SettingSetDateTime::screenSetDate() {
+ Widgets::DotIndicator dotIndicator(0, 2);
+ dotIndicator.Create();
+ return std::make_unique<Screens::SettingSetDate>(app, dateTimeController, *this);
+}
+
+std::unique_ptr<Screen> SettingSetDateTime::screenSetTime() {
+ Widgets::DotIndicator dotIndicator(1, 2);
+ dotIndicator.Create();
+ return std::make_unique<Screens::SettingSetTime>(app, dateTimeController, settingsController, *this);
+}
+
+SettingSetDateTime::~SettingSetDateTime() {
+ lv_obj_clean(lv_scr_act());
+}
+
+void SettingSetDateTime::Advance() {
+ screens.OnTouchEvent(Pinetime::Applications::TouchEvents::SwipeUp);
+}
+
+void SettingSetDateTime::Quit() {
+ running = false;
+}
diff --git a/src/displayapp/screens/settings/SettingSetDateTime.h b/src/displayapp/screens/settings/SettingSetDateTime.h
new file mode 100644
index 00000000..dea283f8
--- /dev/null
+++ b/src/displayapp/screens/settings/SettingSetDateTime.h
@@ -0,0 +1,32 @@
+#pragma once
+
+#include <cstdint>
+#include <lvgl/lvgl.h>
+#include "displayapp/screens/Screen.h"
+#include "displayapp/screens/ScreenList.h"
+
+namespace Pinetime {
+ namespace Applications {
+ namespace Screens {
+ class SettingSetDateTime : public Screen {
+ public:
+ SettingSetDateTime(DisplayApp* app,
+ Pinetime::Controllers::DateTime& dateTimeController,
+ Pinetime::Controllers::Settings& settingsController);
+ ~SettingSetDateTime() override;
+
+ bool OnTouchEvent(TouchEvents event) override;
+ void Advance();
+ void Quit();
+
+ private:
+ Controllers::DateTime& dateTimeController;
+ Controllers::Settings& settingsController;
+
+ ScreenList<2> screens;
+ std::unique_ptr<Screen> screenSetDate();
+ std::unique_ptr<Screen> screenSetTime();
+ };
+ }
+ }
+}
diff --git a/src/displayapp/screens/settings/SettingSetTime.cpp b/src/displayapp/screens/settings/SettingSetTime.cpp
index e7d824fd..67ea7afa 100644
--- a/src/displayapp/screens/settings/SettingSetTime.cpp
+++ b/src/displayapp/screens/settings/SettingSetTime.cpp
@@ -18,6 +18,7 @@ namespace {
screen->SetTime();
}
}
+
void ValueChangedHandler(void* userData) {
auto* screen = static_cast<SettingSetTime*>(userData);
screen->UpdateScreen();
@@ -26,8 +27,9 @@ namespace {
SettingSetTime::SettingSetTime(Pinetime::Applications::DisplayApp* app,
Pinetime::Controllers::DateTime& dateTimeController,
- Pinetime::Controllers::Settings& settingsController)
- : Screen(app), dateTimeController {dateTimeController}, settingsController {settingsController} {
+ Pinetime::Controllers::Settings& settingsController,
+ Pinetime::Applications::Screens::SettingSetDateTime& settingSetDateTime)
+ : Screen(app), dateTimeController {dateTimeController}, settingsController {settingsController}, settingSetDateTime {settingSetDateTime} {
lv_obj_t* title = lv_label_create(lv_scr_act(), nullptr);
lv_label_set_text_static(title, "Set current time");
@@ -74,8 +76,6 @@ SettingSetTime::SettingSetTime(Pinetime::Applications::DisplayApp* app,
lv_obj_set_event_cb(btnSetTime, SetTimeEventHandler);
UpdateScreen();
- lv_obj_set_state(btnSetTime, LV_STATE_DISABLED);
- lv_obj_set_state(lblSetTime, LV_STATE_DISABLED);
}
SettingSetTime::~SettingSetTime() {
@@ -90,8 +90,6 @@ void SettingSetTime::UpdateScreen() {
lv_label_set_text_static(lblampm, "AM");
}
}
- lv_obj_set_state(btnSetTime, LV_STATE_DEFAULT);
- lv_obj_set_state(lblSetTime, LV_STATE_DEFAULT);
}
void SettingSetTime::SetTime() {
@@ -101,11 +99,9 @@ void SettingSetTime::SetTime() {
dateTimeController.SetTime(dateTimeController.Year(),
static_cast<uint8_t>(dateTimeController.Month()),
dateTimeController.Day(),
- static_cast<uint8_t>(dateTimeController.DayOfWeek()),
static_cast<uint8_t>(hoursValue),
static_cast<uint8_t>(minutesValue),
0,
nrf_rtc_counter_get(portNRF_RTC_REG));
- lv_obj_set_state(btnSetTime, LV_STATE_DISABLED);
- lv_obj_set_state(lblSetTime, LV_STATE_DISABLED);
+ settingSetDateTime.Quit();
}
diff --git a/src/displayapp/screens/settings/SettingSetTime.h b/src/displayapp/screens/settings/SettingSetTime.h
index b61962c1..edd89b16 100644
--- a/src/displayapp/screens/settings/SettingSetTime.h
+++ b/src/displayapp/screens/settings/SettingSetTime.h
@@ -6,6 +6,8 @@
#include "components/settings/Settings.h"
#include "displayapp/widgets/Counter.h"
#include "displayapp/screens/Screen.h"
+#include "displayapp/widgets/DotIndicator.h"
+#include "displayapp/screens/settings/SettingSetDateTime.h"
namespace Pinetime {
namespace Applications {
@@ -14,7 +16,8 @@ namespace Pinetime {
public:
SettingSetTime(DisplayApp* app,
Pinetime::Controllers::DateTime& dateTimeController,
- Pinetime::Controllers::Settings& settingsController);
+ Pinetime::Controllers::Settings& settingsController,
+ Pinetime::Applications::Screens::SettingSetDateTime& settingSetDateTime);
~SettingSetTime() override;
void SetTime();
@@ -23,6 +26,7 @@ namespace Pinetime {
private:
Controllers::DateTime& dateTimeController;
Controllers::Settings& settingsController;
+ Pinetime::Applications::Screens::SettingSetDateTime& settingSetDateTime;
lv_obj_t* lblampm;
lv_obj_t* btnSetTime;
diff --git a/src/displayapp/screens/settings/SettingShakeThreshold.cpp b/src/displayapp/screens/settings/SettingShakeThreshold.cpp
index de46f7de..e7edee9a 100644
--- a/src/displayapp/screens/settings/SettingShakeThreshold.cpp
+++ b/src/displayapp/screens/settings/SettingShakeThreshold.cpp
@@ -57,7 +57,7 @@ SettingShakeThreshold::SettingShakeThreshold(DisplayApp* app,
lv_obj_set_width(calButton, 200);
lv_obj_align(calButton, lv_scr_act(), LV_ALIGN_IN_BOTTOM_MID, 0, 0);
lv_btn_set_checkable(calButton, true);
- calLabel = lv_label_create(calButton, NULL);
+ calLabel = lv_label_create(calButton, nullptr);
lv_label_set_text_static(calLabel, "Calibrate");
lv_arc_set_value(positionArc, settingsController.GetShakeThreshold());
@@ -102,7 +102,7 @@ void SettingShakeThreshold::Refresh() {
}
if (xTaskGetTickCount() - vCalTime > pdMS_TO_TICKS(7500)) {
lv_btn_set_state(calButton, LV_STATE_DEFAULT);
- lv_event_send(calButton, LV_EVENT_VALUE_CHANGED, NULL);
+ lv_event_send(calButton, LV_EVENT_VALUE_CHANGED, nullptr);
}
}
if (motionController.currentShakeSpeed() - 300 > lv_arc_get_value(animArc)) {
diff --git a/src/displayapp/screens/settings/SettingShakeThreshold.h b/src/displayapp/screens/settings/SettingShakeThreshold.h
index 43319468..d0979fa6 100644
--- a/src/displayapp/screens/settings/SettingShakeThreshold.h
+++ b/src/displayapp/screens/settings/SettingShakeThreshold.h
@@ -6,6 +6,7 @@
#include "displayapp/screens/Screen.h"
#include <components/motion/MotionController.h>
#include "systemtask/SystemTask.h"
+
namespace Pinetime {
namespace Applications {
diff --git a/src/displayapp/screens/settings/SettingTimeFormat.cpp b/src/displayapp/screens/settings/SettingTimeFormat.cpp
index 5502794b..824a10b2 100644
--- a/src/displayapp/screens/settings/SettingTimeFormat.cpp
+++ b/src/displayapp/screens/settings/SettingTimeFormat.cpp
@@ -8,76 +8,56 @@
using namespace Pinetime::Applications::Screens;
namespace {
- void event_handler(lv_obj_t* obj, lv_event_t event) {
- auto* screen = static_cast<SettingTimeFormat*>(obj->user_data);
- screen->UpdateSelected(obj, event);
- }
-}
-
-constexpr std::array<const char*, 2> SettingTimeFormat::options;
-
-SettingTimeFormat::SettingTimeFormat(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Settings& settingsController)
- : Screen(app), settingsController {settingsController} {
-
- lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
-
- lv_obj_set_style_local_bg_opa(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
- lv_obj_set_style_local_pad_all(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 10);
- lv_obj_set_style_local_pad_inner(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 5);
- lv_obj_set_style_local_border_width(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, 0);
+ struct Option {
+ Pinetime::Controllers::Settings::ClockType clockType;
+ const char* name;
+ };
- lv_obj_set_pos(container1, 10, 60);
- lv_obj_set_width(container1, LV_HOR_RES - 20);
- lv_obj_set_height(container1, LV_VER_RES - 50);
- lv_cont_set_layout(container1, LV_LAYOUT_COLUMN_LEFT);
+ constexpr std::array<Option, 2> options = {{
+ {Pinetime::Controllers::Settings::ClockType::H12, "12-hour"},
+ {Pinetime::Controllers::Settings::ClockType::H24, "24-hour"},
+ }};
- lv_obj_t* title = lv_label_create(lv_scr_act(), nullptr);
- lv_label_set_text_static(title, "Time format");
- lv_label_set_align(title, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(title, lv_scr_act(), LV_ALIGN_IN_TOP_MID, 15, 15);
-
- lv_obj_t* icon = lv_label_create(lv_scr_act(), nullptr);
- lv_obj_set_style_local_text_color(icon, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_ORANGE);
- lv_label_set_text_static(icon, Symbols::clock);
- lv_label_set_align(icon, LV_LABEL_ALIGN_CENTER);
- lv_obj_align(icon, title, LV_ALIGN_OUT_LEFT_MID, -10, 0);
-
- for (unsigned int i = 0; i < options.size(); i++) {
- cbOption[i] = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text(cbOption[i], options[i]);
- cbOption[i]->user_data = this;
- lv_obj_set_event_cb(cbOption[i], event_handler);
- SetRadioButtonStyle(cbOption[i]);
+ std::array<CheckboxList::Item, CheckboxList::MaxItems> CreateOptionArray() {
+ std::array<Pinetime::Applications::Screens::CheckboxList::Item, CheckboxList::MaxItems> optionArray;
+ for (size_t i = 0; i < CheckboxList::MaxItems; i++) {
+ if (i >= options.size()) {
+ optionArray[i].name = "";
+ optionArray[i].enabled = false;
+ } else {
+ optionArray[i].name = options[i].name;
+ optionArray[i].enabled = true;
+ }
+ }
+ return optionArray;
}
- if (settingsController.GetClockType() == Controllers::Settings::ClockType::H12) {
- lv_checkbox_set_checked(cbOption[0], true);
- } else if (settingsController.GetClockType() == Controllers::Settings::ClockType::H24) {
- lv_checkbox_set_checked(cbOption[1], true);
+ uint32_t GetDefaultOption(Pinetime::Controllers::Settings::ClockType currentOption) {
+ for (size_t i = 0; i < options.size(); i++) {
+ if (options[i].clockType == currentOption) {
+ return i;
+ }
+ }
+ return 0;
}
}
-SettingTimeFormat::~SettingTimeFormat() {
- lv_obj_clean(lv_scr_act());
- settingsController.SaveSettings();
+SettingTimeFormat::SettingTimeFormat(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Settings& settingsController)
+ : Screen(app),
+ checkboxList(
+ 0,
+ 1,
+ app,
+ "Time format",
+ Symbols::clock,
+ GetDefaultOption(settingsController.GetClockType()),
+ [&settings = settingsController](uint32_t index) {
+ settings.SetClockType(options[index].clockType);
+ settings.SaveSettings();
+ },
+ CreateOptionArray()) {
}
-void SettingTimeFormat::UpdateSelected(lv_obj_t* object, lv_event_t event) {
- if (event == LV_EVENT_VALUE_CHANGED) {
- for (unsigned int i = 0; i < options.size(); i++) {
- if (object == cbOption[i]) {
- lv_checkbox_set_checked(cbOption[i], true);
-
- if (i == 0) {
- settingsController.SetClockType(Controllers::Settings::ClockType::H12);
- };
- if (i == 1) {
- settingsController.SetClockType(Controllers::Settings::ClockType::H24);
- };
-
- } else {
- lv_checkbox_set_checked(cbOption[i], false);
- }
- }
- }
+SettingTimeFormat::~SettingTimeFormat() {
+ lv_obj_clean(lv_scr_act());
}
diff --git a/src/displayapp/screens/settings/SettingTimeFormat.h b/src/displayapp/screens/settings/SettingTimeFormat.h
index 01ca2c9b..de37f43e 100644
--- a/src/displayapp/screens/settings/SettingTimeFormat.h
+++ b/src/displayapp/screens/settings/SettingTimeFormat.h
@@ -6,6 +6,7 @@
#include "components/settings/Settings.h"
#include "displayapp/screens/Screen.h"
+#include "displayapp/screens/CheckboxList.h"
namespace Pinetime {
@@ -17,12 +18,8 @@ namespace Pinetime {
SettingTimeFormat(DisplayApp* app, Pinetime::Controllers::Settings& settingsController);
~SettingTimeFormat() override;
- void UpdateSelected(lv_obj_t* object, lv_event_t event);
-
private:
- static constexpr std::array<const char*, 2> options = {"12-hour", "24-hour"};
- Controllers::Settings& settingsController;
- lv_obj_t* cbOption[options.size()];
+ CheckboxList checkboxList;
};
}
}
diff --git a/src/displayapp/screens/settings/SettingWakeUp.cpp b/src/displayapp/screens/settings/SettingWakeUp.cpp
index 59275e2f..620fe6e8 100644
--- a/src/displayapp/screens/settings/SettingWakeUp.cpp
+++ b/src/displayapp/screens/settings/SettingWakeUp.cpp
@@ -4,19 +4,23 @@
#include "displayapp/screens/Screen.h"
#include "displayapp/screens/Symbols.h"
#include "components/settings/Settings.h"
+#include "displayapp/screens/Styles.h"
using namespace Pinetime::Applications::Screens;
+constexpr std::array<SettingWakeUp::Option, 4> SettingWakeUp::options;
+
namespace {
void event_handler(lv_obj_t* obj, lv_event_t event) {
auto* screen = static_cast<SettingWakeUp*>(obj->user_data);
- screen->UpdateSelected(obj, event);
+ if (event == LV_EVENT_VALUE_CHANGED) {
+ screen->UpdateSelected(obj);
+ }
}
}
SettingWakeUp::SettingWakeUp(Pinetime::Applications::DisplayApp* app, Pinetime::Controllers::Settings& settingsController)
: Screen(app), settingsController {settingsController} {
- ignoringEvents = false;
lv_obj_t* container1 = lv_cont_create(lv_scr_act(), nullptr);
lv_obj_set_style_local_bg_opa(container1, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
@@ -40,39 +44,15 @@ SettingWakeUp::SettingWakeUp(Pinetime::Applications::DisplayApp* app, Pinetime::
lv_label_set_align(icon, LV_LABEL_ALIGN_CENTER);
lv_obj_align(icon, title, LV_ALIGN_OUT_LEFT_MID, -10, 0);
- optionsTotal = 0;
- cbOption[optionsTotal] = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text_static(cbOption[optionsTotal], "Single Tap");
- cbOption[optionsTotal]->user_data = this;
- lv_obj_set_event_cb(cbOption[optionsTotal], event_handler);
- if (settingsController.isWakeUpModeOn(Pinetime::Controllers::Settings::WakeUpMode::SingleTap)) {
- lv_checkbox_set_checked(cbOption[optionsTotal], true);
- }
- optionsTotal++;
- cbOption[optionsTotal] = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text_static(cbOption[optionsTotal], "Double Tap");
- cbOption[optionsTotal]->user_data = this;
- lv_obj_set_event_cb(cbOption[optionsTotal], event_handler);
- if (settingsController.isWakeUpModeOn(Pinetime::Controllers::Settings::WakeUpMode::DoubleTap)) {
- lv_checkbox_set_checked(cbOption[optionsTotal], true);
- }
- optionsTotal++;
- cbOption[optionsTotal] = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text_static(cbOption[optionsTotal], "Raise Wrist");
- cbOption[optionsTotal]->user_data = this;
- lv_obj_set_event_cb(cbOption[optionsTotal], event_handler);
- if (settingsController.isWakeUpModeOn(Pinetime::Controllers::Settings::WakeUpMode::RaiseWrist)) {
- lv_checkbox_set_checked(cbOption[optionsTotal], true);
- }
- optionsTotal++;
- cbOption[optionsTotal] = lv_checkbox_create(container1, nullptr);
- lv_checkbox_set_text_static(cbOption[optionsTotal], "Shake Wake");
- cbOption[optionsTotal]->user_data = this;
- lv_obj_set_event_cb(cbOption[optionsTotal], event_handler);
- if (settingsController.isWakeUpModeOn(Pinetime::Controllers::Settings::WakeUpMode::Shake)) {
- lv_checkbox_set_checked(cbOption[optionsTotal], true);
+ for (unsigned int i = 0; i < options.size(); i++) {
+ cbOption[i] = lv_checkbox_create(container1, nullptr);
+ lv_checkbox_set_text(cbOption[i], options[i].name);
+ if (settingsController.isWakeUpModeOn(static_cast<Controllers::Settings::WakeUpMode>(i))) {
+ lv_checkbox_set_checked(cbOption[i], true);
+ }
+ cbOption[i]->user_data = this;
+ lv_obj_set_event_cb(cbOption[i], event_handler);
}
- optionsTotal++;
}
SettingWakeUp::~SettingWakeUp() {
@@ -80,32 +60,21 @@ SettingWakeUp::~SettingWakeUp() {
settingsController.SaveSettings();
}
-void SettingWakeUp::UpdateSelected(lv_obj_t* object, lv_event_t event) {
- using WakeUpMode = Pinetime::Controllers::Settings::WakeUpMode;
- if (event == LV_EVENT_VALUE_CHANGED && !ignoringEvents) {
- ignoringEvents = true;
-
- // Find the index of the checkbox that triggered the event
- int index = 0;
- for (; index < optionsTotal; ++index) {
- if (cbOption[index] == object) {
- break;
- }
- }
-
- // Toggle needed wakeup mode
- auto mode = static_cast<WakeUpMode>(index);
- auto currentState = settingsController.isWakeUpModeOn(mode);
- settingsController.setWakeUpMode(mode, !currentState);
-
- // Update checkbox according to current wakeup modes.
- // This is needed because we can have extra logic when setting or unsetting wakeup modes,
- // for example, when setting SingleTap, DoubleTap is unset and vice versa.
- auto modes = settingsController.getWakeUpModes();
- for (int i = 0; i < optionsTotal; ++i) {
- lv_checkbox_set_checked(cbOption[i], modes[i]);
+void SettingWakeUp::UpdateSelected(lv_obj_t* object) {
+ // Find the index of the checkbox that triggered the event
+ for (size_t i = 0; i < options.size(); i++) {
+ if (cbOption[i] == object) {
+ bool currentState = settingsController.isWakeUpModeOn(options[i].wakeUpMode);
+ settingsController.setWakeUpMode(options[i].wakeUpMode, !currentState);
+ break;
}
+ }
- ignoringEvents = false;
+ // Update checkbox according to current wakeup modes.
+ // This is needed because we can have extra logic when setting or unsetting wakeup modes,
+ // for example, when setting SingleTap, DoubleTap is unset and vice versa.
+ auto modes = settingsController.getWakeUpModes();
+ for (size_t i = 0; i < options.size(); ++i) {
+ lv_checkbox_set_checked(cbOption[i], modes[i]);
}
}
diff --git a/src/displayapp/screens/settings/SettingWakeUp.h b/src/displayapp/screens/settings/SettingWakeUp.h
index cd244ae5..2a4e7509 100644
--- a/src/displayapp/screens/settings/SettingWakeUp.h
+++ b/src/displayapp/screens/settings/SettingWakeUp.h
@@ -1,5 +1,6 @@
#pragma once
+#include <array>
#include <cstdint>
#include <lvgl/lvgl.h>
#include "components/settings/Settings.h"
@@ -15,17 +16,23 @@ namespace Pinetime {
SettingWakeUp(DisplayApp* app, Pinetime::Controllers::Settings& settingsController);
~SettingWakeUp() override;
- void UpdateSelected(lv_obj_t* object, lv_event_t event);
+ void UpdateSelected(lv_obj_t* object);
private:
+ struct Option {
+ Controllers::Settings::WakeUpMode wakeUpMode;
+ const char* name;
+ };
+
Controllers::Settings& settingsController;
- uint8_t optionsTotal;
- lv_obj_t* cbOption[5];
- // When UpdateSelected is called, it uses lv_checkbox_set_checked,
- // which can cause extra events to be fired,
- // which might trigger UpdateSelected again, causing a loop.
- // This variable is used as a mutex to prevent that.
- bool ignoringEvents;
+ static constexpr std::array<Option, 4> options = {{
+ {Controllers::Settings::WakeUpMode::SingleTap, "Single Tap"},
+ {Controllers::Settings::WakeUpMode::DoubleTap, "Double Tap"},
+ {Controllers::Settings::WakeUpMode::RaiseWrist, "Raise Wrist"},
+ {Controllers::Settings::WakeUpMode::Shake, "Shake Wake"},
+ }};
+
+ lv_obj_t* cbOption[options.size()];
};
}
}
diff --git a/src/displayapp/screens/settings/SettingWatchFace.cpp b/src/displayapp/screens/settings/SettingWatchFace.cpp
index 217f97b8..da32b5ee 100644
--- a/src/displayapp/screens/settings/SettingWatchFace.cpp
+++ b/src/displayapp/screens/settings/SettingWatchFace.cpp
@@ -1,32 +1,31 @@
#include "displayapp/screens/settings/SettingWatchFace.h"
#include <lvgl/lvgl.h>
#include "displayapp/DisplayApp.h"
-#include "displayapp/screens/CheckboxList.h"
#include "displayapp/screens/Screen.h"
#include "components/settings/Settings.h"
-#include "displayapp/screens/WatchFaceInfineat.h"
-#include "displayapp/screens/WatchFaceCasioStyleG7710.h"
using namespace Pinetime::Applications::Screens;
constexpr const char* SettingWatchFace::title;
constexpr const char* SettingWatchFace::symbol;
+auto SettingWatchFace::CreateScreenList() const {
+ std::array<std::function<std::unique_ptr<Screen>()>, nScreens> screens;
+ for (size_t i = 0; i < screens.size(); i++) {
+ screens[i] = [this, i]() -> std::unique_ptr<Screen> {
+ return CreateScreen(i);
+ };
+ }
+ return screens;
+}
+
SettingWatchFace::SettingWatchFace(Pinetime::Applications::DisplayApp* app,
Pinetime::Controllers::Settings& settingsController,
Pinetime::Controllers::FS& filesystem)
: Screen(app),
settingsController {settingsController},
filesystem {filesystem},
- screens {app,
- 0,
- {[this]() -> std::unique_ptr<Screen> {
- return CreateScreen1();
- },
- [this]() -> std::unique_ptr<Screen> {
- return CreateScreen2();
- }},
- Screens::ScreenListModes::UpDown} {
+ screens {app, 0, CreateScreenList(), Screens::ScreenListModes::UpDown} {
}
SettingWatchFace::~SettingWatchFace() {
@@ -37,32 +36,15 @@ bool SettingWatchFace::OnTouchEvent(Pinetime::Applications::TouchEvents event) {
return screens.OnTouchEvent(event);
}
-std::unique_ptr<Screen> SettingWatchFace::CreateScreen1() {
- std::array<Screens::CheckboxList::Item, 4> watchfaces {
- {{"Digital face", true}, {"Analog face", true}, {"PineTimeStyle", true}, {"Terminal", true}}};
- return std::make_unique<Screens::CheckboxList>(
- 0,
- 2,
- app,
- title,
- symbol,
- settingsController.GetClockFace(),
- [&settings = settingsController](uint32_t clockFace) {
- settings.SetClockFace(clockFace);
- settings.SaveSettings();
- },
- watchfaces);
-}
+std::unique_ptr<Screen> SettingWatchFace::CreateScreen(unsigned int screenNum) const {
+ std::array<Screens::CheckboxList::Item, settingsPerScreen> watchfacesOnThisScreen;
+ for (int i = 0; i < settingsPerScreen; i++) {
+ watchfacesOnThisScreen[i] = watchfaces[screenNum * settingsPerScreen + i];
+ }
-std::unique_ptr<Screen> SettingWatchFace::CreateScreen2() {
- std::array<Screens::CheckboxList::Item, 4> watchfaces {
- {{"Infineat face", Applications::Screens::WatchFaceInfineat::IsAvailable(filesystem)},
- {"Casio G7710", Applications::Screens::WatchFaceCasioStyleG7710::IsAvailable(filesystem)},
- {"", false},
- {"", false}}};
return std::make_unique<Screens::CheckboxList>(
- 1,
- 2,
+ screenNum,
+ nScreens,
app,
title,
symbol,
@@ -71,5 +53,5 @@ std::unique_ptr<Screen> SettingWatchFace::CreateScreen2() {
settings.SetClockFace(clockFace);
settings.SaveSettings();
},
- watchfaces);
+ watchfacesOnThisScreen);
}
diff --git a/src/displayapp/screens/settings/SettingWatchFace.h b/src/displayapp/screens/settings/SettingWatchFace.h
index 158397f8..7b8cdcdc 100644
--- a/src/displayapp/screens/settings/SettingWatchFace.h
+++ b/src/displayapp/screens/settings/SettingWatchFace.h
@@ -8,6 +8,9 @@
#include "components/settings/Settings.h"
#include "displayapp/screens/Screen.h"
#include "displayapp/screens/Symbols.h"
+#include "displayapp/screens/CheckboxList.h"
+#include "displayapp/screens/WatchFaceInfineat.h"
+#include "displayapp/screens/WatchFaceCasioStyleG7710.h"
namespace Pinetime {
@@ -22,14 +25,30 @@ namespace Pinetime {
bool OnTouchEvent(TouchEvents event) override;
private:
+ auto CreateScreenList() const;
+ std::unique_ptr<Screen> CreateScreen(unsigned int screenNum) const;
+
Controllers::Settings& settingsController;
Pinetime::Controllers::FS& filesystem;
- ScreenList<2> screens;
static constexpr const char* title = "Watch face";
static constexpr const char* symbol = Symbols::home;
- std::unique_ptr<Screen> CreateScreen1();
- std::unique_ptr<Screen> CreateScreen2();
+
+ static constexpr int settingsPerScreen = 4;
+
+ // Increment this when more space is needed
+ static constexpr int nScreens = 2;
+
+ std::array<Screens::CheckboxList::Item, settingsPerScreen * nScreens> watchfaces {
+ {{"Digital face", true},
+ {"Analog face", true},
+ {"PineTimeStyle", true},
+ {"Terminal", true},
+ {"Infineat face", Applications::Screens::WatchFaceInfineat::IsAvailable(filesystem)},
+ {"Casio G7710", Applications::Screens::WatchFaceCasioStyleG7710::IsAvailable(filesystem)},
+ {"", false},
+ {"", false}}};
+ ScreenList<nScreens> screens;
};
}
}
diff --git a/src/displayapp/screens/settings/Settings.h b/src/displayapp/screens/settings/Settings.h
index a86db44f..b88c13b7 100644
--- a/src/displayapp/screens/settings/Settings.h
+++ b/src/displayapp/screens/settings/Settings.h
@@ -28,7 +28,7 @@ namespace Pinetime {
static constexpr int entriesPerScreen = 4;
// Increment this when more space is needed
- static constexpr int nScreens = 4;
+ static constexpr int nScreens = 3;
static constexpr std::array<List::Applications, entriesPerScreen * nScreens> entries {{
{Symbols::sun, "Display", Apps::SettingDisplay},
@@ -37,19 +37,20 @@ namespace Pinetime {
{Symbols::home, "Watch face", Apps::SettingWatchFace},
{Symbols::shoe, "Steps", Apps::SettingSteps},
- {Symbols::clock, "Set date", Apps::SettingSetDate},
- {Symbols::clock, "Set time", Apps::SettingSetTime},
+ {Symbols::clock, "Date&Time", Apps::SettingSetDateTime},
{Symbols::batteryHalf, "Battery", Apps::BatteryInfo},
-
{Symbols::clock, "Chimes", Apps::SettingChimes},
+
{Symbols::tachometer, "Shake Calib.", Apps::SettingShakeThreshold},
{Symbols::check, "Firmware", Apps::FirmwareValidation},
{Symbols::bluetooth, "Bluetooth", Apps::SettingBluetooth},
-
{Symbols::list, "About", Apps::SysInfo},
- {Symbols::none, "None", Apps::None},
- {Symbols::none, "None", Apps::None},
- {Symbols::none, "None", Apps::None},
+
+ // {Symbols::none, "None", Apps::None},
+ // {Symbols::none, "None", Apps::None},
+ // {Symbols::none, "None", Apps::None},
+ // {Symbols::none, "None", Apps::None},
+
}};
ScreenList<nScreens> screens;
};
diff --git a/src/displayapp/widgets/Counter.cpp b/src/displayapp/widgets/Counter.cpp
index e95178ec..b486e372 100644
--- a/src/displayapp/widgets/Counter.cpp
+++ b/src/displayapp/widgets/Counter.cpp
@@ -18,6 +18,7 @@ namespace {
widget->DownBtnPressed();
}
}
+
constexpr int digitCount(int number) {
int digitCount = 0;
while (number > 0) {
@@ -28,7 +29,7 @@ namespace {
}
}
-Counter::Counter(int min, int max, lv_font_t& font) : min {min}, max {max}, value {min}, font {font}, leadingZeroCount {digitCount(max)} {
+Counter::Counter(int min, int max, lv_font_t& font) : min {min}, max {max}, value {min}, leadingZeroCount {digitCount(max)}, font {font} {
}
void Counter::UpBtnPressed() {
@@ -67,6 +68,7 @@ void Counter::HideControls() {
lv_obj_set_hidden(lowerLine, true);
lv_obj_set_style_local_bg_opa(counterContainer, LV_OBJ_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
}
+
void Counter::ShowControls() {
lv_obj_set_hidden(upBtn, false);
lv_obj_set_hidden(downBtn, false);
diff --git a/src/displayapp/widgets/DotIndicator.cpp b/src/displayapp/widgets/DotIndicator.cpp
new file mode 100644
index 00000000..209b43bd
--- /dev/null
+++ b/src/displayapp/widgets/DotIndicator.cpp
@@ -0,0 +1,28 @@
+#include "displayapp/widgets/DotIndicator.h"
+#include "displayapp/InfiniTimeTheme.h"
+
+using namespace Pinetime::Applications::Widgets;
+
+DotIndicator::DotIndicator(uint8_t nCurrentScreen, uint8_t nScreens) : nCurrentScreen {nCurrentScreen}, nScreens {nScreens} {
+}
+
+void DotIndicator::Create() {
+ lv_obj_t* dotIndicator[nScreens];
+ static constexpr uint8_t dotSize = 12;
+
+ lv_obj_t* container = lv_cont_create(lv_scr_act(), nullptr);
+ lv_cont_set_layout(container, LV_LAYOUT_COLUMN_LEFT);
+ lv_cont_set_fit(container, LV_FIT_TIGHT);
+ lv_obj_set_style_local_pad_inner(container, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, dotSize);
+ lv_obj_set_style_local_bg_opa(container, LV_CONT_PART_MAIN, LV_STATE_DEFAULT, LV_OPA_TRANSP);
+
+ for (int i = 0; i < nScreens; i++) {
+ dotIndicator[i] = lv_obj_create(container, nullptr);
+ lv_obj_set_size(dotIndicator[i], dotSize, dotSize);
+ lv_obj_set_style_local_bg_color(dotIndicator[i], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_GRAY);
+ }
+
+ lv_obj_set_style_local_bg_color(dotIndicator[nCurrentScreen], LV_BTN_PART_MAIN, LV_STATE_DEFAULT, LV_COLOR_WHITE);
+
+ lv_obj_align(container, nullptr, LV_ALIGN_IN_RIGHT_MID, 0, 0);
+}
diff --git a/src/displayapp/widgets/DotIndicator.h b/src/displayapp/widgets/DotIndicator.h
new file mode 100644
index 00000000..49cdca26
--- /dev/null
+++ b/src/displayapp/widgets/DotIndicator.h
@@ -0,0 +1,18 @@
+#pragma once
+#include <lvgl/lvgl.h>
+
+namespace Pinetime {
+ namespace Applications {
+ namespace Widgets {
+ class DotIndicator {
+ public:
+ DotIndicator(uint8_t nCurrentScreen, uint8_t nScreens);
+ void Create();
+
+ private:
+ uint8_t nCurrentScreen;
+ uint8_t nScreens;
+ };
+ }
+ }
+}
diff --git a/src/displayapp/widgets/StatusIcons.h b/src/displayapp/widgets/StatusIcons.h
index f4a30a80..7d9e3ae3 100644
--- a/src/displayapp/widgets/StatusIcons.h
+++ b/src/displayapp/widgets/StatusIcons.h
@@ -15,9 +15,11 @@ namespace Pinetime {
StatusIcons(Controllers::Battery& batteryController, Controllers::Ble& bleController);
void Align();
void Create();
+
lv_obj_t* GetObject() {
return container;
}
+
void Update();
private:
diff --git a/src/drivers/Bma421.cpp b/src/drivers/Bma421.cpp
index 539cc8d1..84d76ab3 100644
--- a/src/drivers/Bma421.cpp
+++ b/src/drivers/Bma421.cpp
@@ -19,7 +19,7 @@ namespace {
return 0;
}
- void user_delay(uint32_t period_us, void* intf_ptr) {
+ void user_delay(uint32_t period_us, void* /*intf_ptr*/) {
nrf_delay_us(period_us);
}
}
@@ -118,6 +118,7 @@ Bma421::Values Bma421::Process() {
// X and Y axis are swapped because of the way the sensor is mounted in the PineTime
return {steps, data.y, data.x, data.z};
}
+
bool Bma421::IsOk() const {
return isOk;
}
@@ -133,6 +134,7 @@ void Bma421::SoftReset() {
nrf_delay_ms(1);
}
}
+
Bma421::DeviceTypes Bma421::DeviceType() const {
return deviceType;
}
diff --git a/src/drivers/Bma421.h b/src/drivers/Bma421.h
index ac5c707f..fb832514 100644
--- a/src/drivers/Bma421.h
+++ b/src/drivers/Bma421.h
@@ -4,15 +4,18 @@
namespace Pinetime {
namespace Drivers {
class TwiMaster;
+
class Bma421 {
public:
enum class DeviceTypes : uint8_t { Unknown, BMA421, BMA425 };
+
struct Values {
uint32_t steps;
int16_t x;
int16_t y;
int16_t z;
};
+
Bma421(TwiMaster& twiMaster, uint8_t twiAddress);
Bma421(const Bma421&) = delete;
Bma421& operator=(const Bma421&) = delete;
diff --git a/src/drivers/Cst816s.h b/src/drivers/Cst816s.h
index 9d426c9d..c50bb733 100644
--- a/src/drivers/Cst816s.h
+++ b/src/drivers/Cst816s.h
@@ -16,6 +16,7 @@ namespace Pinetime {
DoubleTap = 0x0B,
LongPress = 0x0C
};
+
struct TouchInfos {
uint16_t x = 0;
uint16_t y = 0;
@@ -38,9 +39,11 @@ namespace Pinetime {
uint8_t GetChipId() const {
return chipId;
}
+
uint8_t GetVendorId() const {
return vendorId;
}
+
uint8_t GetFwVersion() const {
return fwVersion;
}
diff --git a/src/drivers/DebugPins.cpp b/src/drivers/DebugPins.cpp
index 4b2f0f16..6d24ca04 100644
--- a/src/drivers/DebugPins.cpp
+++ b/src/drivers/DebugPins.cpp
@@ -18,6 +18,7 @@ void debugpins_init() {
nrf_gpio_cfg_output(DebugPin4);
nrf_gpio_pin_clear(DebugPin4);
}
+
void debugpins_set(debugpins_pins pin) {
nrf_gpio_pin_set(static_cast<uint32_t>(pin));
}
@@ -33,6 +34,7 @@ void debugpins_pulse(debugpins_pins pin) {
#else
void debugpins_init() {
}
+
void debugpins_set(debugpins_pins pin) {
}
diff --git a/src/drivers/DebugPins.h b/src/drivers/DebugPins.h
deleted file mode 100644
index b30cd222..00000000
--- a/src/drivers/DebugPins.h
+++ /dev/null
@@ -1,24 +0,0 @@
-#pragma once
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-#include <stdint.h>
-
-typedef enum {
- DebugPin0 = 27,
- DebugPin1 = 29,
- DebugPin2 = 20,
- DebugPin3 = 17,
- DebugPin4 = 11,
-} debugpins_pins;
-
-void debugpins_init();
-void debugpins_set(debugpins_pins pin);
-void debugpins_clear(debugpins_pins pin);
-void debugpins_pulse(debugpins_pins pin);
-
-#ifdef __cplusplus
-}
-#endif
diff --git a/src/drivers/Hrs3300.cpp b/src/drivers/Hrs3300.cpp
index ec620af2..6c47ae28 100644
--- a/src/drivers/Hrs3300.cpp
+++ b/src/drivers/Hrs3300.cpp
@@ -13,6 +13,7 @@
#include <nrf_log.h>
using namespace Pinetime::Drivers;
+
/** Driver for the HRS3300 heart rate sensor.
* Original implementation from wasp-os : https://github.com/daniel-thompson/wasp-os/blob/master/wasp/drivers/hrs3300.py
*/
diff --git a/src/drivers/SpiMaster.cpp b/src/drivers/SpiMaster.cpp
index 38f72fee..234884ab 100644
--- a/src/drivers/SpiMaster.cpp
+++ b/src/drivers/SpiMaster.cpp
@@ -163,10 +163,7 @@ void SpiMaster::PrepareTx(const volatile uint32_t bufferAddress, const volatile
spiBaseAddress->EVENTS_END = 0;
}
-void SpiMaster::PrepareRx(const volatile uint32_t cmdAddress,
- const volatile size_t cmdSize,
- const volatile uint32_t bufferAddress,
- const volatile size_t size) {
+void SpiMaster::PrepareRx(const volatile uint32_t bufferAddress, const volatile size_t size) {
spiBaseAddress->TXD.PTR = 0;
spiBaseAddress->TXD.MAXCNT = 0;
spiBaseAddress->TXD.LIST = 0;
@@ -234,7 +231,7 @@ bool SpiMaster::Read(uint8_t pinCsn, uint8_t* cmd, size_t cmdSize, uint8_t* data
while (spiBaseAddress->EVENTS_END == 0)
;
- PrepareRx((uint32_t) cmd, cmdSize, (uint32_t) data, dataSize);
+ PrepareRx((uint32_t) data, dataSize);
spiBaseAddress->TASKS_START = 1;
while (spiBaseAddress->EVENTS_END == 0)
diff --git a/src/drivers/SpiMaster.h b/src/drivers/SpiMaster.h
index 5ea624f2..8b698c57 100644
--- a/src/drivers/SpiMaster.h
+++ b/src/drivers/SpiMaster.h
@@ -14,6 +14,7 @@ namespace Pinetime {
enum class BitOrder : uint8_t { Msb_Lsb, Lsb_Msb };
enum class Modes : uint8_t { Mode0, Mode1, Mode2, Mode3 };
enum class Frequencies : uint8_t { Freq8Mhz };
+
struct Parameters {
BitOrder bitOrder;
Modes mode;
@@ -45,10 +46,7 @@ namespace Pinetime {
void SetupWorkaroundForFtpan58(NRF_SPIM_Type* spim, uint32_t ppi_channel, uint32_t gpiote_channel);
void DisableWorkaroundForFtpan58(NRF_SPIM_Type* spim, uint32_t ppi_channel, uint32_t gpiote_channel);
void PrepareTx(const volatile uint32_t bufferAddress, const volatile size_t size);
- void PrepareRx(const volatile uint32_t cmdAddress,
- const volatile size_t cmdSize,
- const volatile uint32_t bufferAddress,
- const volatile size_t size);
+ void PrepareRx(const volatile uint32_t bufferAddress, const volatile size_t size);
NRF_SPIM_Type* spiBaseAddress;
uint8_t pinCsn;
diff --git a/src/drivers/SpiNorFlash.h b/src/drivers/SpiNorFlash.h
index ad4d0907..8a063fea 100644
--- a/src/drivers/SpiNorFlash.h
+++ b/src/drivers/SpiNorFlash.h
@@ -5,6 +5,7 @@
namespace Pinetime {
namespace Drivers {
class Spi;
+
class SpiNorFlash {
public:
explicit SpiNorFlash(Spi& spi);
diff --git a/src/drivers/St7789.h b/src/drivers/St7789.h
index 8c2ac093..8a1bdfca 100644
--- a/src/drivers/St7789.h
+++ b/src/drivers/St7789.h
@@ -5,6 +5,7 @@
namespace Pinetime {
namespace Drivers {
class Spi;
+
class St7789 {
public:
explicit St7789(Spi& spi, uint8_t pinDataCommand);
diff --git a/src/drivers/Watchdog.h b/src/drivers/Watchdog.h
index 03807d61..22aa9df6 100644
--- a/src/drivers/Watchdog.h
+++ b/src/drivers/Watchdog.h
@@ -9,9 +9,11 @@ namespace Pinetime {
void Setup(uint8_t timeoutSeconds);
void Start();
void Kick();
+
ResetReasons ResetReason() const {
return resetReason;
}
+
static const char* ResetReasonToString(ResetReasons reason);
private:
@@ -23,6 +25,7 @@ namespace Pinetime {
public:
WatchdogView(const Watchdog& watchdog) : watchdog {watchdog} {
}
+
Watchdog::ResetReasons ResetReason() const {
return watchdog.ResetReason();
}
diff --git a/src/heartratetask/HeartRateTask.cpp b/src/heartratetask/HeartRateTask.cpp
index bc227624..50833ab2 100644
--- a/src/heartratetask/HeartRateTask.cpp
+++ b/src/heartratetask/HeartRateTask.cpp
@@ -6,15 +6,16 @@
using namespace Pinetime::Applications;
HeartRateTask::HeartRateTask(Drivers::Hrs3300& heartRateSensor, Controllers::HeartRateController& controller)
- : heartRateSensor {heartRateSensor}, controller {controller}, ppg {} {
+ : heartRateSensor {heartRateSensor}, controller {controller} {
}
void HeartRateTask::Start() {
messageQueue = xQueueCreate(10, 1);
controller.SetHeartRateTask(this);
- if (pdPASS != xTaskCreate(HeartRateTask::Process, "Heartrate", 500, this, 0, &taskHandle))
+ if (pdPASS != xTaskCreate(HeartRateTask::Process, "Heartrate", 500, this, 0, &taskHandle)) {
APP_ERROR_HANDLER(NRF_ERROR_NO_MEM);
+ }
}
void HeartRateTask::Process(void* instance) {
@@ -25,17 +26,19 @@ void HeartRateTask::Process(void* instance) {
void HeartRateTask::Work() {
int lastBpm = 0;
while (true) {
- Messages msg;
- uint32_t delay;
+ auto delay = portMAX_DELAY;
if (state == States::Running) {
- if (measurementStarted)
+ if (measurementStarted) {
delay = 40;
- else
+ } else {
delay = 100;
- } else
+ }
+ } else {
delay = portMAX_DELAY;
+ }
- if (xQueueReceive(messageQueue, &msg, delay)) {
+ Messages msg;
+ if (xQueueReceive(messageQueue, &msg, delay) == pdTRUE) {
switch (msg) {
case Messages::GoToSleep:
StopMeasurement();
@@ -49,15 +52,17 @@ void HeartRateTask::Work() {
}
break;
case Messages::StartMeasurement:
- if (measurementStarted)
+ if (measurementStarted) {
break;
+ }
lastBpm = 0;
StartMeasurement();
measurementStarted = true;
break;
case Messages::StopMeasurement:
- if (!measurementStarted)
+ if (!measurementStarted) {
break;
+ }
StopMeasurement();
measurementStarted = false;
break;
@@ -68,8 +73,9 @@ void HeartRateTask::Work() {
ppg.Preprocess(static_cast<float>(heartRateSensor.ReadHrs()));
auto bpm = ppg.HeartRate();
- if (lastBpm == 0 && bpm == 0)
+ if (lastBpm == 0 && bpm == 0) {
controller.Update(Controllers::HeartRateController::States::NotEnoughData, 0);
+ }
if (bpm != 0) {
lastBpm = bpm;
controller.Update(Controllers::HeartRateController::States::Running, lastBpm);
@@ -79,10 +85,9 @@ void HeartRateTask::Work() {
}
void HeartRateTask::PushMessage(HeartRateTask::Messages msg) {
- BaseType_t xHigherPriorityTaskWoken;
- xHigherPriorityTaskWoken = pdFALSE;
+ BaseType_t xHigherPriorityTaskWoken = pdFALSE;
xQueueSendFromISR(messageQueue, &msg, &xHigherPriorityTaskWoken);
- if (xHigherPriorityTaskWoken) {
+ if (xHigherPriorityTaskWoken == pdTRUE) {
/* Actual macro used here is port specific. */
// TODO : should I do something here?
}
@@ -91,7 +96,7 @@ void HeartRateTask::PushMessage(HeartRateTask::Messages msg) {
void HeartRateTask::StartMeasurement() {
heartRateSensor.Enable();
vTaskDelay(100);
- ppg.SetOffset(static_cast<float>(heartRateSensor.ReadHrs()));
+ ppg.SetOffset(heartRateSensor.ReadHrs());
}
void HeartRateTask::StopMeasurement() {
diff --git a/src/heartratetask/HeartRateTask.h b/src/heartratetask/HeartRateTask.h
index 0796dc74..5bbfb9fb 100644
--- a/src/heartratetask/HeartRateTask.h
+++ b/src/heartratetask/HeartRateTask.h
@@ -8,9 +8,11 @@ namespace Pinetime {
namespace Drivers {
class Hrs3300;
}
+
namespace Controllers {
class HeartRateController;
}
+
namespace Applications {
class HeartRateTask {
public:
diff --git a/src/logging/DummyLogger.h b/src/logging/DummyLogger.h
index 1b050b37..53590b6f 100644
--- a/src/logging/DummyLogger.h
+++ b/src/logging/DummyLogger.h
@@ -7,6 +7,7 @@ namespace Pinetime {
public:
void Init() override {
}
+
void Resume() override {
}
};
diff --git a/src/main.cpp b/src/main.cpp
index ad7a07dc..b205f1e6 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -45,7 +45,6 @@
#include "drivers/Cst816s.h"
#include "drivers/PinMap.h"
#include "systemtask/SystemTask.h"
-#include "drivers/PinMap.h"
#include "touchhandler/TouchHandler.h"
#include "buttonhandler/ButtonHandler.h"
@@ -210,29 +209,29 @@ void SPIM0_SPIS0_TWIM0_TWIS0_SPI0_TWI0_IRQHandler(void) {
}
}
-static void (*radio_isr_addr)(void);
-static void (*rng_isr_addr)(void);
-static void (*rtc0_isr_addr)(void);
+static void (*radio_isr_addr)();
+static void (*rng_isr_addr)();
+static void (*rtc0_isr_addr)();
/* Some interrupt handlers required for NimBLE radio driver */
extern "C" {
void RADIO_IRQHandler(void) {
- ((void (*)(void)) radio_isr_addr)();
+ ((void (*)()) radio_isr_addr)();
}
void RNG_IRQHandler(void) {
- ((void (*)(void)) rng_isr_addr)();
+ ((void (*)()) rng_isr_addr)();
}
void RTC0_IRQHandler(void) {
- ((void (*)(void)) rtc0_isr_addr)();
+ ((void (*)()) rtc0_isr_addr)();
}
void WDT_IRQHandler(void) {
nrf_wdt_event_clear(NRF_WDT_EVENT_TIMEOUT);
}
-void npl_freertos_hw_set_isr(int irqn, void (*addr)(void)) {
+void npl_freertos_hw_set_isr(int irqn, void (*addr)()) {
switch (irqn) {
case RADIO_IRQn:
radio_isr_addr = addr;
@@ -243,6 +242,8 @@ void npl_freertos_hw_set_isr(int irqn, void (*addr)(void)) {
case RTC0_IRQn:
rtc0_isr_addr = addr;
break;
+ default:
+ break;
}
}
@@ -253,7 +254,7 @@ uint32_t npl_freertos_hw_enter_critical(void) {
}
void npl_freertos_hw_exit_critical(uint32_t ctx) {
- if (!ctx) {
+ if (ctx == 0) {
__enable_irq();
}
}
@@ -265,15 +266,14 @@ struct ble_npl_eventq* nimble_port_get_dflt_eventq(void) {
}
void nimble_port_run(void) {
- struct ble_npl_event* ev;
-
- while (1) {
- ev = ble_npl_eventq_get(&g_eventq_dflt, BLE_NPL_TIME_FOREVER);
- ble_npl_event_run(ev);
+ struct ble_npl_event* event;
+ while (true) {
+ event = ble_npl_eventq_get(&g_eventq_dflt, BLE_NPL_TIME_FOREVER);
+ ble_npl_event_run(event);
}
}
-void BleHost(void*) {
+void BleHost(void* /*unused*/) {
nimble_port_run();
}
@@ -285,8 +285,7 @@ void nimble_port_init(void) {
ble_hs_init();
ble_store_ram_init();
- int res;
- res = hal_timer_init(5, NULL);
+ int res = hal_timer_init(5, nullptr);
ASSERT(res == 0);
res = os_cputime_init(32768);
ASSERT(res == 0);
@@ -301,17 +300,17 @@ void nimble_port_ll_task_func(void* args) {
}
}
-void calibrate_lf_clock_rc(nrf_drv_clock_evt_type_t event) {
+void calibrate_lf_clock_rc(nrf_drv_clock_evt_type_t /*event*/) {
// 16 * 0.25s = 4s calibration cycle
// Not recursive, call is deferred via internal calibration timer
nrf_drv_clock_calibration_start(16, calibrate_lf_clock_rc);
}
-int main(void) {
+int main() {
logger.Init();
nrf_drv_clock_init();
- nrf_drv_clock_lfclk_request(NULL);
+ nrf_drv_clock_lfclk_request(nullptr);
// When loading the firmware via the Wasp-OS reloader-factory, which uses the used internal LF RC oscillator,
// the LF clock has to be explicitly restarted because InfiniTime uses the external crystal oscillator if available.
diff --git a/src/recoveryLoader.cpp b/src/recoveryLoader.cpp
index 27a79d9c..d6f8d49b 100644
--- a/src/recoveryLoader.cpp
+++ b/src/recoveryLoader.cpp
@@ -81,7 +81,8 @@ void RefreshWatchdog() {
}
uint8_t displayBuffer[displayWidth * bytesPerPixel];
-void Process(void* instance) {
+
+void Process(void* /*instance*/) {
RefreshWatchdog();
APP_GPIOTE_INIT(2);
diff --git a/src/resources/fonts.json b/src/resources/fonts.json
index a270e6a2..c4a63349 100644
--- a/src/resources/fonts.json
+++ b/src/resources/fonts.json
@@ -3,7 +3,7 @@
"sources": [
{
"file": "fonts/Teko-Light.ttf",
- "symbols": "0123456789:/ampMonTueWdhFriSt "
+ "symbols": "0123456789:/APMonTueWdhFriSat "
}
],
"bpp": 1,
diff --git a/src/systemtask/Messages.h b/src/systemtask/Messages.h
index 7a46e060..b7fee8a5 100644
--- a/src/systemtask/Messages.h
+++ b/src/systemtask/Messages.h
@@ -1,8 +1,9 @@
#pragma once
+#include <cstdint>
namespace Pinetime {
namespace System {
- enum class Messages {
+ enum class Messages : uint8_t {
GoToSleep,
GoToRunning,
TouchWakeUp,
@@ -29,6 +30,7 @@ namespace Pinetime {
StopRinging,
MeasureBatteryTimerExpired,
BatteryPercentageUpdated,
+ LowBattery,
StartFileTransfer,
StopFileTransfer,
BleRadioEnableToggle
diff --git a/src/systemtask/SystemTask.cpp b/src/systemtask/SystemTask.cpp
index ef631af7..73f573fa 100644
--- a/src/systemtask/SystemTask.cpp
+++ b/src/systemtask/SystemTask.cpp
@@ -18,6 +18,8 @@
#include "BootErrors.h"
#include <memory>
+#include <algorithm>
+#include <cstring>
using namespace Pinetime::System;
@@ -30,14 +32,14 @@ namespace {
void DimTimerCallback(TimerHandle_t xTimer) {
NRF_LOG_INFO("DimTimerCallback");
- auto sysTask = static_cast<SystemTask*>(pvTimerGetTimerID(xTimer));
+ auto* sysTask = static_cast<SystemTask*>(pvTimerGetTimerID(xTimer));
sysTask->OnDim();
}
void IdleTimerCallback(TimerHandle_t xTimer) {
NRF_LOG_INFO("IdleTimerCallback");
- auto sysTask = static_cast<SystemTask*>(pvTimerGetTimerID(xTimer));
+ auto* sysTask = static_cast<SystemTask*>(pvTimerGetTimerID(xTimer));
sysTask->OnIdle();
}
@@ -208,10 +210,9 @@ void SystemTask::Work() {
while (true) {
UpdateMotion();
- uint8_t msg;
- if (xQueueReceive(systemTasksMsgQueue, &msg, 100)) {
- Messages message = static_cast<Messages>(msg);
- switch (message) {
+ Messages msg;
+ if (xQueueReceive(systemTasksMsgQueue, &msg, 100) == pdTRUE) {
+ switch (msg) {
case Messages::EnableSleeping:
// Make sure that exiting an app doesn't enable sleeping,
// if the exiting was caused by a firmware update
@@ -348,7 +349,7 @@ void SystemTask::Work() {
displayApp.PushMessage(Pinetime::Applications::Display::Messages::TouchEvent);
break;
case Messages::HandleButtonEvent: {
- Controllers::ButtonActions action;
+ Controllers::ButtonActions action = Controllers::ButtonActions::None;
if (nrf_gpio_pin_read(Pinetime::PinMap::Button) == 0) {
action = buttonHandler.HandleEvent(Controllers::ButtonHandler::Events::Release);
} else {
@@ -425,6 +426,16 @@ void SystemTask::Work() {
case Messages::BatteryPercentageUpdated:
nimbleController.NotifyBatteryLevel(batteryController.PercentRemaining());
break;
+ case Messages::LowBattery: {
+ Pinetime::Controllers::NotificationManager::Notification notif;
+ constexpr char message[] = "Low Battery\0Charge your watch to prevent data loss.\0";
+ constexpr size_t messageSize = std::min(sizeof(message), Pinetime::Controllers::NotificationManager::MaximumMessageSize());
+ std::memcpy(notif.message.data(), message, messageSize);
+ notif.size = messageSize;
+ notif.category = Pinetime::Controllers::NotificationManager::Categories::SimpleAlert;
+ notificationManager.Push(std::move(notif));
+ PushMessage(Messages::OnNewNotification);
+ } break;
case Messages::OnPairing:
if (state == SystemTaskState::Sleeping) {
GoToRunning();
@@ -459,7 +470,7 @@ void SystemTask::Work() {
uint32_t systick_counter = nrf_rtc_counter_get(portNRF_RTC_REG);
dateTimeController.UpdateTime(systick_counter);
NoInit_BackUpTime = dateTimeController.CurrentDateTime();
- if (!nrf_gpio_pin_read(PinMap::Button)) {
+ if (nrf_gpio_pin_read(PinMap::Button) == 0) {
watchdog.Kick();
}
}
@@ -552,10 +563,9 @@ void SystemTask::PushMessage(System::Messages msg) {
}
if (in_isr()) {
- BaseType_t xHigherPriorityTaskWoken;
- xHigherPriorityTaskWoken = pdFALSE;
+ BaseType_t xHigherPriorityTaskWoken = pdFALSE;
xQueueSendFromISR(systemTasksMsgQueue, &msg, &xHigherPriorityTaskWoken);
- if (xHigherPriorityTaskWoken) {
+ if (xHigherPriorityTaskWoken == pdTRUE) {
/* Actual macro used here is port specific. */
portYIELD_FROM_ISR(xHigherPriorityTaskWoken);
}
diff --git a/src/systemtask/SystemTask.h b/src/systemtask/SystemTask.h
index d1e4a004..9c43b9b2 100644
--- a/src/systemtask/SystemTask.h
+++ b/src/systemtask/SystemTask.h
@@ -36,6 +36,7 @@
#include "systemtask/Messages.h"
extern std::chrono::time_point<std::chrono::system_clock, std::chrono::nanoseconds> NoInit_BackUpTime;
+
namespace Pinetime {
namespace Drivers {
class Cst816S;
@@ -45,11 +46,13 @@ namespace Pinetime {
class TwiMaster;
class Hrs3300;
}
+
namespace Controllers {
class Battery;
class TouchHandler;
class ButtonHandler;
}
+
namespace System {
class SystemTask {
public:
diff --git a/src/touchhandler/TouchHandler.h b/src/touchhandler/TouchHandler.h
index 332041e5..afce2844 100644
--- a/src/touchhandler/TouchHandler.h
+++ b/src/touchhandler/TouchHandler.h
@@ -6,9 +6,11 @@ namespace Pinetime {
namespace Components {
class LittleVgl;
}
+
namespace Drivers {
class Cst816S;
}
+
namespace Controllers {
class TouchHandler {
public:
@@ -20,12 +22,15 @@ namespace Pinetime {
bool IsTouching() const {
return info.touching;
}
+
uint8_t GetX() const {
return info.x;
}
+
uint8_t GetY() const {
return info.y;
}
+
Pinetime::Applications::TouchEvents GestureGet();
private: