M .github/workflows/main.yml => .github/workflows/main.yml +0 -6
@@ 20,12 20,6 @@ jobs:
fetch-depth: 0
- name: check commit messages
run: ./tools/check_commit_messages.py
- build:
- if: github.event.pull_request.draft == false
- runs-on: self-hosted
- steps:
- - name: build
- run: echo "Placeholder for old CI scripts"
check_copyright_and_style:
name: check copyright and style
if: github.event.pull_request.draft == false
M .github/workflows/releases.yaml => .github/workflows/releases.yaml +21 -6
@@ 27,13 27,17 @@ jobs:
popd
- name: "Build and package for RT1051"
id: build_release_package
+ env:
+ ASSETS_LOGIN: ${{ secrets.ASSETS_LOGIN }}
+ ASSETS_TOKEN: ${{ secrets.ASSETS_TOKEN }}
run: |
./configure.sh rt1051 RelWithDebInfo && \
pushd build-rt1051-RelWithDebInfo && \
export JOBS=${JOBS:-`nproc`} && \
echo "JOBS=${JOBS}" && \
make -j ${JOBS} && \
- make -j ${JOBS} package && \
+ make package-update VERBOSE=1 && \
+ make package-standalone && \
popd && \
./print_last_changes.sh && \
uptime
@@ 48,15 52,26 @@ jobs:
draft: true
prerelease: true
body: ${{steps.build_release_package.outputs.release_notes }}
- - name: Upload Release Package
- id: upload-release-package
+ - name: Upload Standalone Package
+ id: upload-stanalone-package
+ uses: actions/upload-release-asset@v1.0.2
+ env:
+ GITHUB_TOKEN: ${{ secrets.GitHub_PAT }}
+ with:
+ upload_url: ${{ steps.create_release.outputs.upload_url }}
+ # here we have to use relative path with starting "./"
+ asset_path: ./${{ steps.build_release_package.outputs.package_path }}/${{ steps.build_release_package.outputs.package-standalone }}
+ asset_name: ${{ steps.build_release_package.outputs.package-standalone }}
+ asset_content_type: ${{ steps.build_release_package.outputs.standalone-mime_type }}
+ - name: Upload Update Package
+ id: upload-update-package
uses: actions/upload-release-asset@v1.0.2
env:
GITHUB_TOKEN: ${{ secrets.GitHub_PAT }}
with:
upload_url: ${{ steps.create_release.outputs.upload_url }}
# here we have to use relative path with starting "./"
- asset_path: ./${{ steps.build_release_package.outputs.package_path }}/${{steps.build_release_package.outputs.package}}
- asset_name: ${{ steps.build_release_package.outputs.package }}
- asset_content_type: ${{ steps.build_release_package.outputs.mime_type }}
+ asset_path: ./${{ steps.build_release_package.outputs.package_path }}/${{ steps.build_release_package.outputs.package-update }}
+ asset_name: ${{ steps.build_release_package.outputs.package-update }}
+ asset_content_type: ${{ steps.build_release_package.outputs.update-mime_type }}
M .gitmessage => .gitmessage +1 -3
@@ 1,7 1,5 @@
-# Commit subject: [JIRA-TICKET] <Add/Change/Fix> changes summary, don't end with a period
+# Commit subject: [JIRA-TICKET] Changes summary, don't end with a period
# No more than 72 chars. ########################### 72 chars is here: #
-<Title>
-# Remember blank line between title and commit message.
# Commit message: Explain *what* and *why* (not *how*).
# Wrap at 72 chars. ################################### which is here: #
M CMakeLists.txt => CMakeLists.txt +138 -28
@@ 14,6 14,7 @@ include(ModuleConfig)
include(module-lwip/lwip-includes.cmake)
include(SerialPort)
include(CopyGdbInit)
+include(Utils)
message("PROJECT_TARGET: ${PROJECT_TARGET}")
message("TARGET_SOURCES: ${TARGET_SOURCES}")
@@ 218,7 219,14 @@ if (${PROJECT_TARGET} STREQUAL "TARGET_Linux")
DEPENDS ${FAT_IMAGE}
)
add_dependencies(check ${FAT_IMAGE}-target)
- install(TARGETS ${CMAKE_PROJECT_NAME} DESTINATION "./")
+ multicomp_install(
+ TARGETS ${CMAKE_PROJECT_NAME}
+ DESTINATION "./"
+ COMPONENTS Standalone Update
+ )
+ set(CPACK_SYSTEM_NAME "Linux")
+ # only allow the standalone package in Linux config
+ set(CPACK_COMPONENTS_ALL Standalone)
endif()
@@ 249,14 257,63 @@ if (${PROJECT_TARGET} STREQUAL "TARGET_RT1051")
${HEX_FILE}-target ALL
DEPENDS ${CMAKE_BINARY_DIR}/${HEX_FILE}
)
- install(FILES ${CMAKE_BINARY_DIR}/${BIN_FILE}
+
+ multicomp_install(FILES ${CMAKE_BINARY_DIR}/${BIN_FILE}
DESTINATION "./"
PERMISSIONS
OWNER_READ OWNER_WRITE OWNER_EXECUTE
GROUP_READ GROUP_EXECUTE
WORLD_READ WORLD_EXECUTE
+ COMPONENTS Standalone Update
+ )
+
+ # download the bootloader
+ set(ECOBOOT_FILE ${CMAKE_BINARY_DIR}/ecoboot.bin)
+ set(ECOBOOT_DOWNLOAD_LOG ${CMAKE_BINARY_DIR}/download_info.txt)
+
+ if(DEFINED ENV{ASSETS_LOGIN} AND DEFINED ENV{ASSETS_TOKEN})
+ message("ecooboot download with tokens")
+ add_custom_command(OUTPUT ${ECOBOOT_FILE}
+ COMMAND ${CMAKE_SOURCE_DIR}/tools/download_asset.py
+ -l $ENV{ASSETS_LOGIN}
+ -t $ENV{ASSETS_TOKEN}
+ -w ${CMAKE_BINARY_DIR} ecoboot download
+ > ${ECOBOOT_DOWNLOAD_LOG}
+ COMMENT "Downloading ecoboot.bin"
+ BYPRODUCTS ${ECOBOOT_FILE} ${ECOBOOT_DOWNLOAD_LOG}
+ )
+ else()
+ message("ecoboot download with git")
+ add_custom_command(OUTPUT ${ECOBOOT_FILE}
+ COMMAND ${CMAKE_SOURCE_DIR}/tools/download_asset.py
+ -w ${CMAKE_BINARY_DIR} ecoboot download
+ > ${ECOBOOT_DOWNLOAD_LOG}
+ COMMENT "Downloading ecoboot.bin"
+ BYPRODUCTS ${ECOBOOT_FILE} ${ECOBOOT_DOWNLOAD_LOG}
)
+ endif()
+
+ add_custom_target(ecoboot.bin DEPENDS ${ECOBOOT_FILE})
+
+ # generate version.json file (runs CMake script at build time)
+ set(VERSION_JSON ${CMAKE_BINARY_DIR}/version.json)
+ add_custom_command(OUTPUT ${VERSION_JSON}
+ COMMAND ${CMAKE_COMMAND}
+ -DSRC_DIR=${CMAKE_SOURCE_DIR}
+ -DECOBOOT_DOWNLOAD_LOG=${ECOBOOT_DOWNLOAD_LOG}
+ -B ${CMAKE_BINARY_DIR}
+ -P ${CMAKE_SOURCE_DIR}/config/GenUpdateVersionJson.cmake
+ DEPENDS ecoboot.bin ${ECOBOOT_DOWNLOAD_LOG}
+ BYPRODUCTS ${VERSION_JSON}
+ )
+ add_custom_target(version.json DEPENDS ${VERSION_JSON})
+
+ multicomp_install(PROGRAMS ${ECOBOOT_FILE} DESTINATION "./" COMPONENTS Standalone Update)
+ multicomp_install(FILES ${VERSION_JSON} DESTINATION "./" COMPONENTS Standalone Update)
+
set(CPACK_SYSTEM_NAME "RT1051")
+ # allow both standalone and update packages in RT1051 config
+ set(CPACK_COMPONENTS_ALL Standalone Update)
endif()
if (${CMAKE_BUILD_TYPE} STREQUAL "Release")
@@ 265,8 322,10 @@ if (${CMAKE_BUILD_TYPE} STREQUAL "Release")
)
endif()
-install(FILES ${PROJECT_SOURCE_DIR}/changelog.md
+install(
+ FILES ${PROJECT_SOURCE_DIR}/changelog.md
DESTINATION "./"
+ COMPONENT Standalone
)
if (${CMAKE_BUILD_TYPE} STREQUAL "RelWithDebInfo")
@@ 280,11 339,6 @@ if (${CMAKE_BUILD_TYPE} STREQUAL "RelWithDebInfo")
)
endif()
-add_custom_target(ecoboot.bin
- COMMAND ${CMAKE_SOURCE_DIR}/tools/download_asset.py -w ${CMAKE_BINARY_DIR}/update ecoboot download
- BYPRODUCTS update/ecoboot.bin
- )
-
message_serial_status()
option (BUILD_DOC_WITH_ALL "Build documentation" OFF)
@@ 321,39 375,95 @@ else ()
endif ()
message("SRC DIR: ${CMAKE_SOURCE_DIR}")
+
include(Version)
+configure_file(
+ ${SRC_DIR}/source/version.hpp.template
+ ${CMAKE_BINARY_DIR}/source/version.hpp
+ )
add_custom_target(
version ALL
- COMMAND
- ${CMAKE_COMMAND} -DSRC_DIR=${CMAKE_SOURCE_DIR} -B ${CMAKE_BINARY_DIR} -P ${CMAKE_SOURCE_DIR}/config/Version.cmake
+ COMMAND ${CMAKE_COMMAND}
+ -DSRC_DIR=${CMAKE_SOURCE_DIR}
+ -B ${CMAKE_BINARY_DIR}
+ -P ${CMAKE_SOURCE_DIR}/config/GenVersionHpp.cmake
COMMENT
- "Generationg version info"
+ "Generating version info"
)
-
add_dependencies(${PROJECT_NAME} version)
set(CPACK_PACKAGE_VENDOR "Mudita")
+set(CPACK_PACKAGE_NAME "PurePhone")
set(CPACK_PACKAGE_HOMEPAGE_URL "https://mudita.com/products/pure/")
-if (${PROJECT_TARGET} STREQUAL "TARGET_RT1051")
- set(CPACK_GENERATOR "ZIP")
- set(PACKAGE_EXTENSION ".zip")
- set(PACKAGE_MIME "application/zip")
-else()
- set(CPACK_GENERATOR "TGZ")
- set(PACKAGE_EXTENSION ".tar.gz")
- set(PACKAGE_MIME "application/x-compressed-tar")
-endif()
+set(CPACK_TOPLEVEL_TAG ${CPACK_SYSTEM_NAME})
+# the CPACK_PACKAGE_FILE_NAME variable will be reset after include(CPack) hence a copy
+set(PACKAGE_COMMON_NAME ${CPACK_PACKAGE_NAME}-${CMAKE_PROJECT_VERSION}-${CPACK_TOPLEVEL_TAG})
+set(CPACK_PACKAGE_FILE_NAME ${PACKAGE_COMMON_NAME})
+# setting this will CPack prevent from additing the default 'package' target
+set(CPACK_OUTPUT_CONFIG_FILE ${CMAKE_BINARY_DIR}/PackageConfig.cmake)
+set(CPACK_GENERATOR "External")
+set(CPACK_COMPONENTS_GROUPING IGNORE)
+set(CPACK_EXTERNAL_ENABLE_STAGING TRUE)
+set(PACKAGE_STAGING_DIRECTORY ${CMAKE_BINARY_DIR}/_CPack_Packages/${CPACK_TOPLEVEL_TAG}/${CPACK_GENERATOR}/${CPACK_PACKAGE_FILE_NAME})
include(CPack)
-if (NOT "$ENV{GITHUB_WORKSPACE}" STREQUAL "")
- set(PACKAGE_FILE ${CPACK_PACKAGE_NAME}-${CPACK_PACKAGE_VERSION}-${CPACK_SYSTEM_NAME}${PACKAGE_EXTENSION})
-
- message("set-output name=package::${PACKAGE_FILE}")
- message("::set-output name=package::${PACKAGE_FILE}")
+add_custom_target(package-standalone-staged
+ COMMAND ${CMAKE_CPACK_COMMAND}
+ -C $<CONFIGURATION>
+ --config ${CPACK_OUTPUT_CONFIG_FILE}
+ )
- message("set-output name=mime_type::${PACKAGE_MIME}")
- message("::set-output name=mime_type::${PACKAGE_MIME}")
+if (${PROJECT_TARGET} STREQUAL "TARGET_RT1051")
+ set(PACKAGE_STANDALONE_FILE_NAME ${PACKAGE_COMMON_NAME}-Standalone.zip)
+ set(PACKAGE_STANDALONE_MIME "application/zip")
+ add_custom_target(package-update-staged
+ COMMAND ${CMAKE_CPACK_COMMAND}
+ -C $<CONFIGURATION>
+ --config ${CPACK_OUTPUT_CONFIG_FILE}
+ DEPENDS ecoboot.bin version.json
+ )
+ add_custom_target(package-standalone
+ COMMAND zip -rq ${CMAKE_BINARY_DIR}/${PACKAGE_STANDALONE_FILE_NAME} "."
+ WORKING_DIRECTORY ${PACKAGE_STAGING_DIRECTORY}/Standalone
+ DEPENDS ${ECOBOOT_FILE} package-standalone-staged PurePhone
+ )
+ set(UPDATE_STAGING_DIRECTORY ${PACKAGE_STAGING_DIRECTORY}/Update)
+ add_custom_target(package-update-checksums
+ COMMAND rhash
+ -u checksums.txt
+ -r .
+ WORKING_DIRECTORY ${UPDATE_STAGING_DIRECTORY}
+ DEPENDS package-update-staged
+ )
+ set(PACKAGE_UPDATE_FILE_NAME ${PACKAGE_COMMON_NAME}-Update.tar)
+ set(PACKAGE_UPDATE_MIME "application/x-tar")
+ add_custom_target(package-update
+ COMMAND tar
+ -cf ${CMAKE_BINARY_DIR}/${PACKAGE_UPDATE_FILE_NAME}
+ -C ${PACKAGE_STAGING_DIRECTORY}/Update "."
+ DEPENDS ecoboot.bin version.json PurePhone package-update-staged package-update-checksums
+ )
+elseif (${PROJECT_TARGET} STREQUAL "TARGET_Linux")
+ set(PACKAGE_STANDALONE_FILE_NAME ${PACKAGE_COMMON_NAME}-Standalone.tar.gz)
+ set(PACKAGE_STANDALONE_MIME "application/x-compressed-tar")
+ add_custom_target(package-standalone
+ COMMAND tar
+ -czf ${CMAKE_BINARY_DIR}/${PACKAGE_STANDALONE_FILE_NAME}
+ -C ${PACKAGE_STAGING_DIRECTORY}/Standalone "."
+ DEPENDS package-standalone-staged
+ )
endif()
+if (NOT "$ENV{GITHUB_WORKSPACE}" STREQUAL "")
+ message("set-output name=package-standalone::${PACKAGE_STANDALONE_FILE_NAME}")
+ message("::set-output name=package-standalone::${PACKAGE_STANDALONE_FILE_NAME}")
+ message("set-output name=standalone-mime_type::${PACKAGE_STANDALONE_MIME}")
+ message("::set-output name=standalone-mime_type::${PACKAGE_STANDALONE_MIME}")
+
+ message("set-output name=package-update::${PACKAGE_UPDATE_FILE_NAME}")
+ message("::set-output name=package-update::${PACKAGE_UPDATE_FILE_NAME}")
+ message("set-output name=update-mime_type::${PACKAGE_UPDATE_MIME}")
+ message("::set-output name=update-mime_type::${PACKAGE_UPDATE_MIME}")
+endif()
M LICENSE.md => LICENSE.md +2 -0
@@ 3,6 3,8 @@
MuditaOS – https://github.com/mudita/MuditaOS
Copyright (c) 2017-2021, Mudita Sp. z o.o. All rights reserved.
+MuditaOS is licensed under GNU GPLv3.
+
## Sources of Intellectual Property Included in MuditaOS
Where not otherwise indicated, all MuditaOS content is authored by Mudita engineers and consists of Mudita-owned intellectual property. In some specific instances, MuditaOS will incorporate work done by developers outside of Mudita with their expressed permission.
M changelog.md => changelog.md +3 -1
@@ 29,7 29,9 @@
### Added
* Add hardware in the loop tests.
-* Add empty APN settings window.
+* Add APN settings window.
+* Add New/Edit APN window
+* Add APN options window
### Changed
A config/GenUpdateVersionJson.cmake => config/GenUpdateVersionJson.cmake +21 -0
@@ 0,0 1,21 @@
+# This script generates the version.json file which contains project
+# and bootloader version information for update packages . It is meant to be run
+# at build time by running CMake as a target.
+
+list(APPEND CMAKE_MODULE_PATH "${SRC_DIR}/config")
+include(Version)
+
+set(BOOTLOADER_INCLUDED "true")
+set(BOOTLOADER_FILENAME "ecoboot.bin")
+execute_process(
+ COMMAND grep "release:" "${ECOBOOT_DOWNLOAD_LOG}"
+ COMMAND awk "{print $2}"
+ OUTPUT_VARIABLE BOOTLOADER_VERSION
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+)
+
+configure_file(
+ ${SRC_DIR}/config/version.json.cmake_template
+ ${CMAKE_BINARY_DIR}/version.json
+ @ONLY
+ )
A config/GenVersionHpp.cmake => config/GenVersionHpp.cmake +14 -0
@@ 0,0 1,14 @@
+# This script generates the source/version.hpp containing project version
+# information. It is meant to be run at build time by running CMake as a target.
+
+list(APPEND CMAKE_MODULE_PATH "${SRC_DIR}/config")
+include(Version)
+
+configure_file(
+ ${SRC_DIR}/source/version.hpp.template
+ ${CMAKE_BINARY_DIR}/source/version.hpp
+ )
+
+message("GIT_REV: ${GIT_REV}")
+message("GIT_TAG: ${GIT_TAG}")
+message("Version: ${CMAKE_PROJECT_VERSION}")
M config/ProjectConfig.cmake => config/ProjectConfig.cmake +12 -1
@@ 26,15 26,26 @@ else()
set (LOG_LUART_ENABLED 0 CACHE INTERNAL "")
endif()
+# add Mudita USB Vendor/Product IDs
+option(MUDITA_USB_ID "Enables using Mudita registered USB Vendor ID and Pure Phone USB Product ID" OFF)
+if (MUDITA_USB_ID)
+ set (USB_DEVICE_VENDOR_ID 0x3310 CACHE INTERNAL "Sets USB_DEVICE_VENDOR_ID to Mudita Vendor ID")
+ set (USB_DEVICE_PRODUCT_ID 0x0100 CACHE INTERNAL "Sets USB_DEVICE_PRODUCT_ID to Mudita Pure Product ID")
+else()
+ set (USB_DEVICE_VENDOR_ID 0x045E CACHE INTERNAL "Sets USB_DEVICE_VENDOR_ID to Microsoft Vendor ID")
+ set (USB_DEVICE_PRODUCT_ID 0x0622 CACHE INTERNAL "Sets USB_DEVICE_PRODUCT_ID to Windows MTP Simulator Product ID")
+endif()
+
#Config options described in README.md
set(PROJECT_CONFIG_DEFINITIONS
-
LOG_USE_COLOR=${LOG_USE_COLOR}
LOG_REDIRECT=${LOG_REDIRECT}
SYSTEM_VIEW_ENABLED=${SYSTEM_VIEW_ENABLED}
USBCDC_ECHO_ENABLED=${USBCDC_ECHO_ENABLED}
LOG_LUART_ENABLED=${LOG_LUART_ENABLED}
PROJECT_CONFIG_USER_DYNMEM_SIZE=9*1024*1024
+ USB_DEVICE_VENDOR_ID=${USB_DEVICE_VENDOR_ID}
+ USB_DEVICE_PRODUCT_ID=${USB_DEVICE_PRODUCT_ID}
CACHE INTERNAL ""
)
A config/Utils.cmake => config/Utils.cmake +13 -0
@@ 0,0 1,13 @@
+# An equivalent of install() which allows to declare multiple components using
+# a custom 'COMPONENTS' clause. This clause must be the last on the
+# argument list. The original 'COMPONENT' from install() clause must not appear
+# on the argument list.
+function(multicomp_install)
+ list(FIND ARGN "COMPONENTS" CLAUSE_INDEX)
+ list(SUBLIST ARGN 0 ${CLAUSE_INDEX} INSTALL_ARGN)
+ math(EXPR COMPS_INDEX "${CLAUSE_INDEX}+1")
+ list(SUBLIST ARGN ${COMPS_INDEX} ${ARGC} COMPONENTS)
+ foreach(COMP IN LISTS COMPONENTS)
+ install(${INSTALL_ARGN} COMPONENT ${COMP})
+ endforeach()
+endfunction()
M config/Version.cmake => config/Version.cmake +34 -22
@@ 1,9 1,8 @@
-# from: https://www.mattkeeter.com/blog/2018-01-06-versioning/
+# from: https://www.mattkeeter.com/blog/2018-01-06-versioning/ (modified)
-set(VERSION_HEADER "${CMAKE_BINARY_DIR}/source/version.hpp")
-
-execute_process(COMMAND git log --pretty=format:'%h' -n 1
+execute_process(COMMAND git rev-parse --short HEAD
OUTPUT_VARIABLE GIT_REV
+ OUTPUT_STRIP_TRAILING_WHITESPACE
ERROR_QUIET)
if ( NOT SRC_DIR )
@@ 21,38 20,51 @@ else()
execute_process(
COMMAND bash -c "git diff --quiet --exit-code || echo +"
OUTPUT_VARIABLE GIT_DIFF
+ OUTPUT_STRIP_TRAILING_WHITESPACE
WORKING_DIRECTORY ${SRC_DIR}
)
execute_process(
COMMAND git describe --tags
- OUTPUT_VARIABLE GIT_TAG ERROR_QUIET RESULT_VARIABLE ret
+ RESULT_VARIABLE ret
+ OUTPUT_VARIABLE GIT_TAG
+ OUTPUT_STRIP_TRAILING_WHITESPACE
WORKING_DIRECTORY ${SRC_DIR}
+ ERROR_QUIET
)
if(NOT ret EQUAL "0")
set(GIT_TAG "none")
endif()
execute_process(
COMMAND git rev-parse --abbrev-ref HEAD
- OUTPUT_VARIABLE GIT_BRANCH)
-
- string(STRIP "${GIT_REV}" GIT_REV)
- string(SUBSTRING "${GIT_REV}" 1 7 GIT_REV)
- string(STRIP "${GIT_DIFF}" GIT_DIFF)
- string(STRIP "${GIT_TAG}" GIT_TAG)
- string(STRIP "${GIT_BRANCH}" GIT_BRANCH)
+ OUTPUT_VARIABLE GIT_BRANCH
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
+ execute_process(
+ COMMAND uname -r
+ OUTPUT_VARIABLE BUILD_HOST
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
+ execute_process(
+ COMMAND git config user.name
+ OUTPUT_VARIABLE BUILD_USER
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
+ execute_process(
+ COMMAND date +%F-%T
+ OUTPUT_VARIABLE BUILD_DATE
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
+ execute_process(
+ COMMAND grep tskKERNEL_VERSION_NUMBER ${SRC_DIR}/module-os/FreeRTOS/include/task.h
+ COMMAND awk "{print $3}"
+ COMMAND tr -d "\""
+ OUTPUT_VARIABLE KERNEL_VERSION
+ OUTPUT_STRIP_TRAILING_WHITESPACE
+ )
endif()
-message("GIT_REV: ${GIT_REV}")
-message("GIT_TAG: ${GIT_TAG}")
string(REGEX MATCH "release-([0-9]*).([0-9]*).([0-9]*)" VERSION_RAW ${GIT_TAG})
-
set(CMAKE_PROJECT_VERSION_MAJOR "${CMAKE_MATCH_1}")
set(CMAKE_PROJECT_VERSION_MINOR "${CMAKE_MATCH_2}")
set(CMAKE_PROJECT_VERSION_PATCH "${CMAKE_MATCH_3}")
-
-message("Vession: ${CMAKE_PROJECT_VERSION_MAJOR}.${CMAKE_PROJECT_VERSION_MINOR}.${CMAKE_PROJECT_VERSION_PATCH}")
-
-configure_file(
- ${SRC_DIR}/source/version.hpp.template
- ${CMAKE_BINARY_DIR}/source/version.hpp
- )
+set(CMAKE_PROJECT_VERSION "${CMAKE_PROJECT_VERSION_MAJOR}.${CMAKE_PROJECT_VERSION_MINOR}.${CMAKE_PROJECT_VERSION_PATCH}")
A config/version.json.cmake_template => config/version.json.cmake_template +29 -0
@@ 0,0 1,29 @@
+{
+ "git":
+ {
+ "git_branch": "@GIT_BRANCH@",
+ "git_commit": "@GIT_REV@",
+ "git_tag": "@GIT_TAG@"
+ },
+ "misc":
+ {
+ "codename": "@VERSION_CODENAME@",
+ "kernel": "@KERNEL_VERSION@",
+ "buildon": "@BUILD_HOST@",
+ "builddate": "@BUILD_DATE@",
+ "builduser": "@BUILD_USER@"
+ },
+ "version":
+ {
+ "major": "@CMAKE_PROJECT_VERSION_MAJOR@",
+ "minor": "@CMAKE_PROJECT_VERSION_MINOR@",
+ "patch": "@CMAKE_PROJECT_VERSION_PATCH@",
+ "string": "@CMAKE_PROJECT_VERSION@"
+ },
+ "bootloader":
+ {
+ "included": "@BOOTLOADER_INCLUDED@",
+ "version": "@BOOTLOADER_VERSION@",
+ "filename": "@BOOTLOADER_FILENAME@"
+ }
+}
M doc/development_workflow.md => doc/development_workflow.md +10 -9
@@ 15,18 15,19 @@ Each commit that makes it from your branch or fork into the master branch must h
If you're part of the MuditaOS core development team, your commit's title *must* start with a Jira ticket number in square brackets e.g. `[EGD-5555]`.
Commits from the community will be accompanied by a relevant Jira ticket number during the merge. Don't add commits that are out of the scope of the Jira issue you are working on.
+You should have exactly one commit in a single PR.
Your commit's subject line should be a single sentence describing what you are changing using present simple tense and an imperative mood. Please follow these rules:
-- It must start with one of the following verbs: "Add", "Change" or "Fix", depending on whether you are adding a new feature, changing its behavior, or fixing it. This sentence will be a part of the project changelog, so please ensure it will be clear to the non-technical readers.
+- It must start with a verb. This sentence will be a part of the project changelog, so please ensure it will be clear to the non-technical readers.
+- If you are adding a new feature start with "Add"; start with "Fix" if you are fixing one.
- Don't use proper names such as names of classes or functions.
- Try to be as concise as possible in the limit of 72 characters (including the Jira ticket number - 11 characters).
- Don't end the subject line with a period.
Then, in the commit message, you must include a short description of what the commit is changing in the project. You should be clear about
your motivation to do the change and how it influences the project.
-
-If it's impossible to provide any of the above information, then your commit is likely excessive or redundant and should be squashed with another commit.
+Focus more on *why* than *how*.
An example of a correctly formatted commit:
```
@@ 50,13 51,13 @@ You can add a commit template and hook that will help with proper defining both
Before submitting a Pull Request please go through some basic checks:
-- test your changes on both Linux and RT1051 platforms (please pay special attention to the things you might break unintentionally, e.g. when working on calling funcionality, check call log too)
-- [include changelog description](changelog_howto.md) (if applicable),
+- test your changes on both Linux and RT1051 platforms (please pay special attention to the things you might break unintentionally, e.g. when working on calling, check call log too,
- run unit tests (`make check`),
+- [run static analysis](static_analysis.md)
- check if your code formatting complies with [`.clang-format`](../clang-format),
-- whenever you add a third party software to MuditaOS source code, please make sure that the software component is added to a dedicated [section in `LICENSE.md` file on MuditaOS GitHub repository](../LICENSE.md) with a link to the text of the license where applicable.
+- whenever you add third-party software to MuditaOS source code, please make sure that the software component is added to a dedicated [section in `LICENSE.md` file on MuditaOS GitHub repository](../LICENSE.md) with a link to the text of the license where applicable.
-As a part of our continuous integration proccess we will be soon introducing our own [test harness](../test/README.md).
+As a part of our continuous integration process we will be soon introducing our own [test harness](../test/README.md).
## Submit a Pull Request
@@ 78,7 79,7 @@ During a PR review, team members will ask you questions regarding your solution.
## PR review - act on feedback
-Add changes to your PR that are requested by reviewers and push the feature branch once again. Update comments requesting changes with a simple `Done`. Don't resolve discussion on your own, it's the reviewer's responsibility to do so.
+Add changes to your PR that are requested by reviewers and push the feature branch once again. Update comments requesting changes with a simple `Done`. Don't resolve a discussion on your own, it's the reviewer's responsibility to do so.
## Merge to `master` branch
@@ 110,7 111,7 @@ git rebase origin/master # update branch you are at to origin/master
`Rebase` changes your commit history (moves them on top). This means two things:
- - when you did a lot of changes in a lot of places - either `git push` your branch on server, or make its copy
+ - when you did a lot of changes in a lot of places - either `git push` your branch to the server, or make its copy
- when you're happy of `git rebase` results - you'll need to push your branch with force to server - since you've changed its history (updated it)
A minimal set of commands:
M doc/quickstart.md => doc/quickstart.md +3 -3
@@ 148,14 148,14 @@ To fix the style for Pull Request CI:
### Commit message template
-To add commit message template use this command:
+To add a commit message template use this command:
```bash
git config commit.template .gitmessage
```
-This way each time you add new commit you will see template that will help
-you with proper message format. More about that in (Development Workflow)[./doc/development_workflow.md#commit-changes]
+This way each time you add a new commit you will see the template that will help
+you with the proper message format. More about that in (Development Workflow)[./doc/development_workflow.md#commit-changes]
### Commit message hook
This hooks automatically converts your branch name to commit title
A doc/static_analysis.md => doc/static_analysis.md +31 -0
@@ 0,0 1,31 @@
+# Static code analysis
+
+The Static code analysis is a method of debugging that is done by examining the source code without executing the program.
+
+Before submitting the Pull Request a developer should run static code analyzer tool and make sure that his code complies with the Coding Standards.
+
+## Clang-tidy
+
+The clang-tidy is a clang-based C++ “linter” tool. Its purpose is to provide an extensible framework for diagnosing and fixing typical programming errors, like style violations, interface misuse, or bugs that can be deduced via static analysis.
+
+### Install clang-tidy
+
+#### Linux Ubuntu
+
+The clang-tidy tool is available from the APT repository.
+
+`$ sudo apt install clang-tidy`
+
+### Run clang-tidy
+
+If `run-clang-tidy` program is installed, a CMake target called `clang-tidy` is available.
+
+In order to run `clang-tidy` analyzer on the MuditaOS repository, follow the steps:
+```
+$ cd <path/to/MuditaOS>
+$ ./configure.sh <platform> <build_type>
+$ cd <path/to/build/dir>
+$ make clang-tidy
+```
+
+The results of the analysis are available under `$(pwd)/StaticAnalysis` directory.
M host-tools/CMakeLists.txt => host-tools/CMakeLists.txt +11 -2
@@ 6,9 6,18 @@ if (CMAKE_CROSSCOMPILING)
COMMAND ${CMAKE_COMMAND}
-DCMAKE_BUILD_TYPE:STRING="Release"
-DCMAKE_RUNTIME_OUTPUT_DIRECTORY_RELEASE:PATH="${CMAKE_BINARY_DIR}"
- -B"build"
+ -B"lfsfuse"
-H"${CMAKE_SOURCE_DIR}/host-tools/littlefs-fuse"
- COMMAND ${CMAKE_COMMAND} --build build --config Release
+ COMMAND ${CMAKE_COMMAND} --build lfsfuse --config Release
+ )
+ add_custom_target(
+ genlittlefs ALL
+ COMMAND ${CMAKE_COMMAND}
+ -DCMAKE_BUILD_TYPE:STRING="Release"
+ -DCMAKE_RUNTIME_OUTPUT_DIRECTORY_RELEASE:PATH="${CMAKE_BINARY_DIR}"
+ -B"genlittlefs"
+ -H"${CMAKE_SOURCE_DIR}/host-tools/genlittlefs"
+ COMMAND ${CMAKE_COMMAND} --build genlittlefs --config Release
)
else()
set(_genlittlefs "${CMAKE_BINARY_DIR}/genlittlefs${CMAKE_EXECUTABLE_SUFFIX}")
M host-tools/genlittlefs/CMakeLists.txt => host-tools/genlittlefs/CMakeLists.txt +7 -0
@@ 5,6 5,13 @@ set(CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/CMake" ${CMAKE_MODULE_PATH})
find_package(BLKID REQUIRED)
+# only add LittleFS subdirectory during a standalone config of genlittlefs
+if (CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
+ add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/../../module-vfs/thirdparty/lfsfs
+ ${CMAKE_CURRENT_BINARY_DIR}/lfsfs EXCLUDE_FROM_ALL
+ )
+endif()
+
set(GENLITTLEFS_SRCS
mklfs.c
parse_partitions.c
M host-tools/genlittlefs/mklfs.c => host-tools/genlittlefs/mklfs.c +2 -2
@@ 186,7 186,7 @@ static int add_to_lfs(lfs_t *lfs, const char *dir, struct lfs_info_summary *summ
tgt_dir[0] = '/';
strcpy(tgt_dir + 1, sep_ptr + 1);
}
- int err;
+ int err = 0;
if (is_dir) {
err = create_dir_in_lfs(lfs, tgt_dir, verbose);
if (err) {
@@ 240,7 240,7 @@ static void configure_lfs_params(struct lfs_config *lfsc, const struct littlefs_
int main(int argc, char **argv)
{
- int err;
+ int err = 0;
struct littlefs_opts lopts;
struct lfs_config cfg;
struct lfs_info_summary prog_summary;
M image/CMakeLists.txt => image/CMakeLists.txt +12 -3
@@ 1,4 1,6 @@
-set(ASSETS_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}")
+include(Utils)
+
+set(ASSETS_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}")
set(ASSETS_DEST_DIR "${CMAKE_BINARY_DIR}")
file (GLOB_RECURSE ASSETS_LIST
@@ 16,10 18,17 @@ foreach(ASSET ${ASSETS_LIST})
if(dir)
set(destdir "${ASSETS_DEST_DIR}/${dir}")
- install(FILES ${ASSET} DESTINATION ${dir})
+ multicomp_install(
+ FILES ${ASSET}
+ DESTINATION ${dir}
+ COMPONENTS Standalone Update
+ )
else()
set(destdir "${ASSETS_DEST_DIR}")
- install(FILES ${ASSET} DESTINATION "./" )
+ multicomp_install(
+ FILES ${ASSET}
+ DESTINATION "./"
+ COMPONENTS Standalone Update)
endif()
set(outfile "${destdir}/${filename}")
M image/assets/lang/Deutsch.json => image/assets/lang/Deutsch.json +1 -0
@@ 38,6 38,7 @@
"common_yesterday": "Yesterday",
"common_today": "Today",
"locale_12hour_min": "%I:%M %p",
+ "locale_12hour_min_short": "%I:%M",
"locale_24hour_min": "%H:%M",
"locale_date_full": "%m/%d/%y",
"locale_date_short": "%d/%m",
M image/assets/lang/English.json => image/assets/lang/English.json +25 -4
@@ 62,6 62,7 @@
"common_search": "SEARCH",
"common_empty_list": "Default Info: No elements on list.",
"locale_12hour_min": "%I:%M %p",
+ "locale_12hour_min_short": "%I:%M",
"locale_24hour_min": "%H:%M",
"locale_date_full": "%m/%d/%y",
"locale_date_short": "%d/%m",
@@ 299,12 300,17 @@
"app_settings_display_input_language": "Input language",
"app_settings_display_locked_screen_autolock": "Autolock",
"app_settings_display_locked_screen_wallpaper": "Wallpaper",
- "app_settings_display_locked_screen_quotes": "Quotes",
- "app_settings_display_locked_screen_new_quote": "New quote",
"app_settings_display_wallpaper_logo": "Mudita logo",
"app_settings_display_wallpaper_clock": "Clock",
"app_settings_display_wallpaper_quotes": "Quotes",
- "app_settings_display_wallpaper_select_quotes": "Select Quotes",
+ "app_settings_display_wallpaper_quotes_options": "Options",
+ "app_settings_display_wallpaper_quotes_edit": "Edit quote",
+ "app_settings_display_wallpaper_quotes_delete": "Delete quote",
+ "app_settings_display_wallpaper_quotes_new": "New quote",
+ "app_settings_display_wallpaper_quotes_select": "Select quotes",
+ "app_settings_display_wallpaper_quotes_delete_confirmation": "Delete quote?",
+ "app_settings_display_wallpaper_quotes_quote": "Quote text",
+ "app_settings_display_wallpaper_quotes_author": "Quote author",
"app_settings_system": "System",
"app_settings_apps_tools": "Apps and tools",
"app_settings_apps_messages": "Messages",
@@ 328,6 334,9 @@
"app_settings_phone_modes": "Phone Modes",
"app_settings_security": "Security",
"app_settings_language": "Language",
+ "app_settings_factory_reset": "Factory reset",
+ "app_settings_about_your_pure": "About your Pure",
+ "app_settings_certification": "Certification",
"app_settings_about": "About Mudita Pure",
"app_settings_title_languages": "Language Selection",
"app_settings_language_english": "English",
@@ 343,7 352,6 @@
"app_settings_network_sim_none": "No Sim",
"app_settings_network_voice_over_lte" : "VoLTE (experimental)",
"app_settings_network_apn_settings" : "APN settings",
- "app_settings_network_apn_settings_no_apns" : "<text align='center' color='9'>No APNs yet.<p>Press <b>left arrow</b> to add new.</p></text>",
"app_settings_toggle_on": "ON",
"app_settings_toggle_off": "OFF",
"app_settings_security_lock_screen_passcode": "Lock screen passcode",
@@ 354,6 362,19 @@
"app_settings_security_wrong_passcode": "Wrong passcode!",
"app_settings_security_passcode_changed_successfully": "Passcode changed successfully!",
"app_settings_security_passcode_disabled": "Passcode disabled!",
+ "app_settings_apn_settings_no_apns" : "<text align='center' color='9'>No APNs yet.<p>Press <b>left arrow</b> to add new.</p></text>",
+ "app_settings_apn_options" : "Options",
+ "app_settings_apn_options_delete" : "Delete",
+ "app_settings_apn_options_edit" : "Edit",
+ "app_settings_apn_options_set_as_default" : "Set as default",
+ "app_settings_new_edit_apn": "New/Edit APN",
+ "app_settings_apn_name": "Name",
+ "app_settings_apn_APN": "APN",
+ "app_settings_apn_username": "UserName",
+ "app_settings_apn_password": "Password",
+ "app_settings_apn_authtype": "Authentication type",
+ "app_settings_apn_apntype": "APN Type",
+ "app_settings_apn_apnprotocol" : "APN Protocol",
"app_phonebook_title_main": "Contacts",
"app_phonebook_search_win_contacts": "Contacts",
"common_search_uc": "Search",
M image/assets/lang/Espanol.json => image/assets/lang/Espanol.json +1 -0
@@ 38,6 38,7 @@
"common_yesterday": "Yesterday",
"common_today": "Today",
"locale_12hour_min": "%I:%M %p",
+ "locale_12hour_min_short": "%I:%M",
"locale_24hour_min": "%H:%M",
"locale_date_full": "%m/%d/%y",
"locale_date_short": "%d/%m",
M image/assets/lang/Francais.json => image/assets/lang/Francais.json +1 -0
@@ 38,6 38,7 @@
"common_yesterday": "Yesterday",
"common_today": "Today",
"locale_12hour_min": "%I:%M %p",
+ "locale_12hour_min_short": "%I:%M",
"locale_24hour_min": "%H:%M",
"locale_date_full": "%m/%d/%y",
"locale_date_short": "%d/%m",
M image/assets/lang/Polski.json => image/assets/lang/Polski.json +1 -0
@@ 38,6 38,7 @@
"common_yesterday": "wczoraj",
"common_today": "dzisiaj",
"locale_12hour_min": "%I:%M",
+ "locale_12hour_min_short": "%I:%M",
"locale_24hour_min": "%H:%M",
"locale_date_full": "%d.%m.%y",
"locale_date_short": "%d.%m",
A image/user/data/applications/settings/quotes.json => image/user/data/applications/settings/quotes.json +27 -0
@@ 0,0 1,27 @@
+[
+ {
+ "lang":"english",
+ "author": "Buddha",
+ "quote": "Do not dwell in the past, do not dream of the future, concentrate the mind on the present moment."
+ },
+ {
+ "lang":"english",
+ "author": "Tara Brach",
+ "quote": "The only way to live is by accepting each minute as an unrepeatable miracle."
+ },
+ {
+ "lang":"english",
+ "author": "Richar Bach",
+ "quote": "The simplest things are often the truest"
+ },
+ {
+ "lang":"english",
+ "author": "Eckhart Tolle",
+ "quote": "Always say yes to the present moment. Say yes to life."
+ },
+ {
+ "lang":"english",
+ "author": "Naomi Judd",
+ "quote": "Slow down, simplify and be kind"
+ }
+]
M module-apps/Application.cpp => module-apps/Application.cpp +38 -28
@@ 2,31 2,31 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "Application.hpp"
-#include "Common.hpp" // for RefreshModes
-#include "GuiTimer.hpp" // for GuiTimer
-#include "Item.hpp" // for Item
-#include "MessageType.hpp" // for MessageType
-#include "Service/Timer.hpp" // for Timer
-#include "Timer.hpp" // for Timer
-#include "Translator.hpp" // for KeyInputSim...
-#include "common_data/EventStore.hpp" // for Battery
-#include "common_data/RawKey.hpp" // for RawKey, key...
-#include "gui/input/InputEvent.hpp" // for InputEvent
-#include "log/debug.hpp" // for DEBUG_APPLI...
-#include "log/log.hpp" // for LOG_INFO
-#include "messages/AppMessage.hpp" // for AppSwitchMe...
-#include "service-appmgr/Controller.hpp" // for Controller
+#include "Common.hpp" // for RefreshModes
+#include "GuiTimer.hpp" // for GuiTimer
+#include "Item.hpp" // for Item
+#include "MessageType.hpp" // for MessageType
+#include "Service/Timer.hpp" // for Timer
+#include "Timer.hpp" // for Timer
+#include "Translator.hpp" // for KeyInputSim...
+#include "common_data/EventStore.hpp" // for Battery
+#include "common_data/RawKey.hpp" // for RawKey, key...
+#include "gui/input/InputEvent.hpp" // for InputEvent
+#include "log/debug.hpp" // for DEBUG_APPLI...
+#include "log/log.hpp" // for LOG_INFO
+#include "messages/AppMessage.hpp" // for AppSwitchMe...
+#include "service-appmgr/Controller.hpp" // for Controller
#include <service-cellular/CellularMessage.hpp>
#include <service-evtmgr/BatteryMessages.hpp>
#include <service-evtmgr/Constants.hpp>
#include <service-evtmgr/EVMessages.hpp>
-#include "service-gui/messages/DrawMessage.hpp" // for DrawMessage
-#include "task.h" // for xTaskGetTic...
-#include "windows/AppWindow.hpp" // for AppWindow
-#include <Text.hpp> // for Text
-#include <algorithm> // for find
-#include <iterator> // for distance, next
-#include <type_traits> // for add_const<>...
+#include "service-gui/messages/DrawMessage.hpp" // for DrawMessage
+#include "task.h" // for xTaskGetTic...
+#include "windows/AppWindow.hpp" // for AppWindow
+#include <Text.hpp> // for Text
+#include <algorithm> // for find
+#include <iterator> // for distance, next
+#include <type_traits> // for add_const<>...
#include <WindowsFactory.hpp>
#include <service-gui/Common.hpp>
#include <module-utils/Utils.hpp>
@@ 70,10 70,12 @@ namespace app
uint32_t stackDepth,
sys::ServicePriority priority)
: Service(std::move(name), std::move(parent), stackDepth, priority),
- default_window(gui::name::window::main_window), windowsStack(this), startInBackground{startInBackground},
- callbackStorage{std::make_unique<CallbackStorage>()}, settings(std::make_unique<settings::Settings>(this))
+ default_window(gui::name::window::main_window), windowsStack(this),
+ keyTranslator{std::make_unique<gui::KeyInputSimpleTranslation>()}, startInBackground{startInBackground},
+ callbackStorage{std::make_unique<CallbackStorage>()}, topBarManager{std::make_unique<TopBarManager>()},
+ settings(std::make_unique<settings::Settings>(this))
{
- keyTranslator = std::make_unique<gui::KeyInputSimpleTranslation>();
+ topBarManager->enableIndicators({gui::top_bar::Indicator::Time});
busChannels.push_back(sys::BusChannels::ServiceCellularNotifications);
longPressTimer = std::make_unique<sys::Timer>("LongPress", this, key_timer_ms);
@@ 82,13 84,16 @@ namespace app
connect(typeid(AppRefreshMessage),
[this](sys::Message *msg) -> sys::MessagePointer { return handleAppRefresh(msg); });
- settings->registerValueChange(settings::SystemProperties::timeFormat12,
- [this](std::string value) { timeFormatChanged(value); });
+ settings->registerValueChange(
+ settings::SystemProperties::timeFormat12,
+ [this](std::string value) { timeFormatChanged(value); },
+ settings::SettingsScope::Global);
}
Application::~Application() noexcept
{
windowsStack.windows.clear();
+ settings->unregisterValueChange();
}
Application::State Application::getState()
@@ 104,7 109,6 @@ namespace app
state = st;
}
-
void Application::longPressTimerCallback()
{
// TODO if(check widget type long press trigger)
@@ 497,7 501,8 @@ namespace app
settings->registerValueChange(
settings::SystemProperties::lockScreenPasscodeIsOn,
- [this](const std::string &value) { setLockScreenPasscodeOn(utils::getNumericValue<bool>(value)); });
+ [this](const std::string &value) { setLockScreenPasscodeOn(utils::getNumericValue<bool>(value)); },
+ settings::SettingsScope::Global);
return sys::ReturnCodes::Success;
}
@@ 694,6 699,11 @@ namespace app
item->attachTimer(std::move(timer));
}
+ const gui::top_bar::Configuration &Application::getTopBarConfiguration() const noexcept
+ {
+ return topBarManager->getConfiguration();
+ }
+
void Application::addActionReceiver(manager::actions::ActionId actionId, OnActionReceived &&callback)
{
receivers.insert_or_assign(actionId, std::move(callback));
M module-apps/Application.hpp => module-apps/Application.hpp +4 -0
@@ 25,6 25,7 @@
#include <string> // for string
#include <utility> // for move, pair
#include <vector> // for vector
+#include "TopBarManager.hpp"
#include "WindowsFactory.hpp"
#include "WindowsStack.hpp"
@@ 369,6 370,8 @@ namespace app
void addActionReceiver(manager::actions::ActionId actionId, OnActionReceived &&callback);
+ std::unique_ptr<TopBarManager> topBarManager;
+
/// application's settings
std::unique_ptr<settings::Settings> settings;
virtual void timeFormatChanged(std::string value);
@@ 378,6 381,7 @@ namespace app
bool isTimeFormat12() const noexcept;
void setLockScreenPasscodeOn(bool screenPasscodeOn) noexcept;
bool isLockScreenPasscodeOn() const noexcept;
+ const gui::top_bar::Configuration &getTopBarConfiguration() const noexcept;
};
/// Parameter pack used by application launch action.
M module-apps/CMakeLists.txt => module-apps/CMakeLists.txt +1 -0
@@ 15,6 15,7 @@ set( SOURCES
"Application.cpp"
"GuiTimer.cpp"
"WindowsFactory.cpp"
+ "TopBarManager.cpp"
"AsyncTask.cpp"
"CallbackStorage.cpp"
"windows/AppWindow.cpp"
A module-apps/TopBarManager.cpp => module-apps/TopBarManager.cpp +17 -0
@@ 0,0 1,17 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "TopBarManager.hpp"
+
+namespace app
+{
+ void TopBarManager::enableIndicators(const gui::top_bar::Indicators &indicators)
+ {
+ topBarConfiguration.enable(indicators);
+ }
+
+ auto TopBarManager::getConfiguration() const noexcept -> const gui::top_bar::Configuration &
+ {
+ return topBarConfiguration;
+ }
+} // namespace app
A module-apps/TopBarManager.hpp => module-apps/TopBarManager.hpp +19 -0
@@ 0,0 1,19 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include <TopBar.hpp>
+
+namespace app
+{
+ class TopBarManager
+ {
+ public:
+ void enableIndicators(const gui::top_bar::Indicators &indicators);
+ [[nodiscard]] auto getConfiguration() const noexcept -> const gui::top_bar::Configuration &;
+
+ private:
+ gui::top_bar::Configuration topBarConfiguration;
+ };
+} // namespace app
M module-apps/application-alarm-clock/windows/AlarmClockMainWindow.cpp => module-apps/application-alarm-clock/windows/AlarmClockMainWindow.cpp +0 -1
@@ 32,7 32,6 @@ namespace app::alarmClock
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
bottomBar->setText(gui::BottomBar::Side::CENTER, utils::localize.get(style::strings::common::Switch));
M module-apps/application-alarm-clock/windows/CustomRepeatWindow.cpp => module-apps/application-alarm-clock/windows/CustomRepeatWindow.cpp +0 -3
@@ 18,9 18,6 @@ namespace app::alarmClock
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
- topBar->setActive(gui::TopBar::Elements::SIM, false);
- topBar->setActive(gui::TopBar::Elements::NETWORK_ACCESS_TECHNOLOGY, false);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setActive(gui::BottomBar::Side::CENTER, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-alarm-clock/windows/NewEditAlarmWindow.cpp => module-apps/application-alarm-clock/windows/NewEditAlarmWindow.cpp +0 -1
@@ 21,7 21,6 @@ namespace app::alarmClock
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setActive(gui::BottomBar::Side::CENTER, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-antenna/windows/AlgoParamsWindow.cpp => module-apps/application-antenna/windows/AlgoParamsWindow.cpp +0 -4
@@ 39,10 39,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::TIME, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
setTitle(utils::localize.get("app_desktop_tools_antenna"));
lowBandBox = new gui::VBox(this,
M module-apps/application-antenna/windows/AntennaMainWindow.cpp => module-apps/application-antenna/windows/AntennaMainWindow.cpp +0 -4
@@ 48,10 48,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::TIME, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
setTitle(utils::localize.get("app_desktop_tools_antenna"));
for (auto title : titlesText) {
M module-apps/application-antenna/windows/ScanModesWindow.cpp => module-apps/application-antenna/windows/ScanModesWindow.cpp +0 -4
@@ 37,10 37,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::TIME, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
setTitle(utils::localize.get("app_desktop_tools_antenna"));
modeButtonParams.insert(std::pair<uint32_t, std::string>(scanModes::Auto, "AUTO"));
M module-apps/application-calculator/data/CalculatorUtility.cpp => module-apps/application-calculator/data/CalculatorUtility.cpp +70 -0
@@ 15,6 15,9 @@ Result Calculator::calculate(std::string source)
double result = te_interp(source.c_str(), &error);
if (error == 0 && !std::isinf(result) && !std::isnan(result)) {
auto output = utils::to_string(result);
+ if (output.length() > CalculatorConstants::maxStringLength) {
+ output = getValueThatFitsOnScreen(result);
+ }
if (utils::localize.get("app_calculator_decimal_separator") == style::calculator::symbols::strings::comma) {
output.replace(output.find(style::calculator::symbols::strings::full_stop),
std::size(std::string_view(style::calculator::symbols::strings::full_stop)),
@@ 48,3 51,70 @@ std::string Calculator::replaceAllOccurrences(std::string input, const std::stri
}
return input;
}
+
+std::string Calculator::getValueThatFitsOnScreen(double result)
+{
+ auto base = static_cast<long long>(result);
+ auto length = utils::to_string(base).length();
+ if (base < 0) {
+ length -= 1;
+ }
+ if (length > CalculatorConstants::expLength + 1) {
+ return convertToNumberWithPositiveExponent(result, length - 1);
+ }
+ else if (length == CalculatorConstants::expLength + 1) {
+ if (result < 0) {
+ return utils::to_string(getCoefficient(result, CalculatorConstants::veryLowPrecision));
+ }
+ return utils::to_string(getCoefficient(result, CalculatorConstants::lowPrecision));
+ }
+ else if (length == 1 && result < -1) {
+ return utils::to_string(getCoefficient(result, CalculatorConstants::lowPrecision));
+ }
+ else if (result > 1) {
+ return utils::to_string(getCoefficient(result, CalculatorConstants::precision));
+ }
+ else {
+ return convertToNumberWithNegativeExponent(result, base);
+ }
+}
+
+std::string Calculator::convertToNumberWithPositiveExponent(double result, uint32_t exponent)
+{
+ result /= pow(10, exponent);
+ auto exponentLength = utils::to_string(exponent).length();
+ auto decimalPlace = CalculatorConstants::precision - exponentLength - CalculatorConstants::expLength;
+ if (result < 0) {
+ decimalPlace -= 1;
+ }
+ return utils::to_string(getCoefficient(result, decimalPlace)) + "e" + utils::to_string(exponent);
+}
+
+std::string Calculator::convertToNumberWithNegativeExponent(double result, long long base)
+{
+ double frac = (result - base) * pow(10, CalculatorConstants::highPrecision);
+ if (result < 0) {
+ frac *= -1;
+ }
+ auto fractionalPart = static_cast<unsigned long int>(round(frac));
+ auto fracLength = utils::to_string(fractionalPart).length();
+ auto exponent = CalculatorConstants::highPrecision - fracLength + 1;
+ if (exponent > CalculatorConstants::minusExpLength + 1) {
+ result *= pow(10, exponent);
+ auto exponentLength = utils::to_string(exponent).length();
+ auto decimalPlace = CalculatorConstants::precision - exponentLength - CalculatorConstants::minusExpLength;
+ if (result < 0) {
+ decimalPlace -= 1;
+ }
+ return utils::to_string(getCoefficient(result, decimalPlace)) + "e-" + utils::to_string(exponent);
+ }
+ else if (result < 0) {
+ return utils::to_string(getCoefficient(result, CalculatorConstants::lowPrecision));
+ }
+ return utils::to_string(getCoefficient(result, CalculatorConstants::precision));
+}
+
+long double Calculator::getCoefficient(double result, uint32_t precision)
+{
+ return std::roundl(result * pow(10, precision)) / pow(10, precision);
+}
M module-apps/application-calculator/data/CalculatorUtility.hpp => module-apps/application-calculator/data/CalculatorUtility.hpp +15 -0
@@ 4,6 4,17 @@
#pragma once
#include <string>
+namespace CalculatorConstants
+{
+ inline constexpr auto veryLowPrecision = 4;
+ inline constexpr auto lowPrecision = 5;
+ inline constexpr auto precision = 6;
+ inline constexpr auto highPrecision = 8;
+ inline constexpr auto expLength = 1;
+ inline constexpr auto minusExpLength = 2;
+ inline constexpr auto maxStringLength = 7;
+} // namespace CalculatorConstants
+
struct Result
{
std::string equation;
@@ 18,6 29,10 @@ class Calculator
/// @return: new string with replaced all occurrences of given string to the new one in whole input
std::string replaceAllOccurrences(std::string input, const std::string &from, const std::string &to);
std::string prepareEquationForParser(std::string input);
+ std::string getValueThatFitsOnScreen(double result);
+ long double getCoefficient(double result, uint32_t precision);
+ std::string convertToNumberWithPositiveExponent(double result, uint32_t exponent);
+ std::string convertToNumberWithNegativeExponent(double result, long long base);
public:
Result calculate(std::string source);
M module-apps/application-calculator/tests/CalculatorUtility_tests.cpp => module-apps/application-calculator/tests/CalculatorUtility_tests.cpp +47 -0
@@ 103,4 103,51 @@ TEST_CASE("Calculator utilities")
REQUIRE(result.equation == "1.79769e+308*2");
REQUIRE(result.isError);
}
+
+ SECTION("Round to fit in screen")
+ {
+ auto result = calculator.calculate("1.1234512345");
+ REQUIRE(result.value == "1.123451");
+ REQUIRE(!result.isError);
+
+ result = calculator.calculate("0.0567891");
+ REQUIRE(result.value == "0.056789");
+ REQUIRE(!result.isError);
+
+ result = calculator.calculate("-0.056789");
+ REQUIRE(result.value == "-0.05679");
+ REQUIRE(!result.isError);
+
+ result = calculator.calculate("15.556789");
+ REQUIRE(result.value == "15.55679");
+ REQUIRE(!result.isError);
+ }
+
+ SECTION("Change to scientific notation (number > 0)")
+ {
+ auto result = calculator.calculate("12345.55555");
+ REQUIRE(result.value == "1.2346e4");
+ REQUIRE(!result.isError);
+ }
+
+ SECTION("Change to scientific notation (number < 0)")
+ {
+ auto result = calculator.calculate("-12345.55555");
+ REQUIRE(result.value == "-1.235e4");
+ REQUIRE(!result.isError);
+ }
+
+ SECTION("Change to scientific notation (0 < number < 1)")
+ {
+ auto result = calculator.calculate("0.000456712");
+ REQUIRE(result.value == "4.567e-4");
+ REQUIRE(!result.isError);
+ }
+
+ SECTION("Change to scientific notation (-1 < number < 0)")
+ {
+ auto result = calculator.calculate("-0.000456712");
+ REQUIRE(result.value == "-4.57e-4");
+ REQUIRE(!result.isError);
+ }
}
M module-apps/application-calculator/widgets/CalculatorStyle.hpp => module-apps/application-calculator/widgets/CalculatorStyle.hpp +1 -0
@@ 34,6 34,7 @@ namespace style::calculator
inline constexpr auto full_stop = 0x002E;
inline constexpr auto comma = 0x002C;
inline constexpr auto equals = 0x003D;
+ inline constexpr auto zero = 0x0030;
} // namespace codes
namespace strings
M module-apps/application-calculator/windows/CalculatorMainWindow.cpp => module-apps/application-calculator/windows/CalculatorMainWindow.cpp +42 -7
@@ 63,8 63,15 @@ namespace gui
if (!event.isShortPress()) {
return false;
}
+ if (event.is(gui::KeyCode::KEY_0) && mathOperationInput->getText() == "0") {
+ return true;
+ }
auto lastChar = mathOperationInput->getText()[mathOperationInput->getText().length() - 1];
bool lastCharIsSymbol = isSymbol(lastChar);
+ if (lastChar == style::calculator::symbols::codes::zero && isSymbol(getPenultimate()) &&
+ !isDecimalSeparator(getPenultimate()) && event.is(gui::KeyCode::KEY_0)) {
+ return true;
+ }
if (event.keyCode == gui::KeyCode::KEY_UP) {
writeEquation(lastCharIsSymbol, style::calculator::symbols::strings::plus);
return true;
@@ 89,6 96,15 @@ namespace gui
}
return true;
}
+ if (lastChar == style::calculator::symbols::codes::zero && isSymbol(getPenultimate()) &&
+ !isDecimalSeparator(getPenultimate()) && !event.is(gui::KeyCode::KEY_0) &&
+ !event.is(gui::KeyCode::KEY_PND) && !event.is(gui::KeyCode::KEY_ENTER)) {
+ mathOperationInput->removeChar();
+ return false;
+ }
+ if (!event.is(gui::KeyCode::KEY_0) && mathOperationInput->getText() == "0") {
+ mathOperationInput->clear();
+ }
return false;
};
}
@@ 103,21 119,36 @@ namespace gui
character == style::calculator::symbols::codes::full_stop;
}
+ bool CalculatorMainWindow::isDecimalSeparator(uint32_t character)
+ {
+ return character == style::calculator::symbols::codes::comma ||
+ character == style::calculator::symbols::codes::full_stop;
+ }
+
+ uint32_t CalculatorMainWindow::getPenultimate()
+ {
+ if (mathOperationInput->getText().length() > 1) {
+ return mathOperationInput->getText()[mathOperationInput->getText().length() - 2];
+ }
+ return 0;
+ }
+
void CalculatorMainWindow::writeEquation(bool lastCharIsSymbol, const UTF8 &symbol)
{
if (!mathOperationInput->getText().empty()) {
if (lastCharIsSymbol && symbol != style::calculator::symbols::strings::minus) {
- mathOperationInput->setRichText(
- std::string(mathOperationInput->getText()).erase(mathOperationInput->getText().length() - 1) +
- symbol.c_str());
+ if (!isSymbol(getPenultimate()) && mathOperationInput->getText().length() > 1) {
+ mathOperationInput->removeChar();
+ mathOperationInput->addText(symbol);
+ }
}
else {
- mathOperationInput->setRichText(mathOperationInput->getText() + symbol);
+ mathOperationInput->addText(symbol);
}
}
else if (symbol == style::calculator::symbols::strings::minus) {
- mathOperationInput->setRichText(mathOperationInput->getText() + symbol);
+ mathOperationInput->addText(symbol);
}
}
@@ 126,7 157,11 @@ namespace gui
if (!mathOperationInput->getText().empty()) {
std::vector<int> symbolsIndexes;
auto input = std::string(mathOperationInput->getText()).erase(mathOperationInput->getText().length() - 1);
- symbolsIndexes.push_back(input.find_last_of(style::calculator::symbols::strings::minus));
+ auto exponentIndex = input.find_last_of('e');
+ auto minusIndex = input.find_last_of(style::calculator::symbols::strings::minus);
+ if (minusIndex != exponentIndex + 1) {
+ symbolsIndexes.push_back(minusIndex);
+ }
symbolsIndexes.push_back(input.find_last_of(style::calculator::symbols::strings::plus));
symbolsIndexes.push_back(input.find_last_of(style::calculator::symbols::strings::division));
symbolsIndexes.push_back(input.find_last_of(style::calculator::symbols::strings::multiplication));
@@ 156,7 191,7 @@ namespace gui
if (inputEvent.keyCode == gui::KeyCode::KEY_ENTER) {
auto result = Calculator().calculate(std::string(mathOperationInput->getText()));
- mathOperationInput->setRichText(result.value);
+ mathOperationInput->setText(result.value);
clearInput = result.isError;
return true;
}
M module-apps/application-calculator/windows/CalculatorMainWindow.hpp => module-apps/application-calculator/windows/CalculatorMainWindow.hpp +2 -0
@@ 22,6 22,8 @@ namespace gui
void applyInputCallback();
bool isPreviousNumberDecimal();
bool isSymbol(uint32_t character);
+ bool isDecimalSeparator(uint32_t character);
+ uint32_t getPenultimate();
public:
CalculatorMainWindow(app::Application *app, std::string name);
M module-apps/application-calendar/ApplicationCalendar.cpp => module-apps/application-calendar/ApplicationCalendar.cpp +1 -1
@@ 147,7 147,7 @@ namespace app
void ApplicationCalendar::destroyUserInterface()
{}
- void ApplicationCalendar::switchToNoEventsWindow(const std::string &title, const TimePoint &dateFilter)
+ void ApplicationCalendar::switchToNoEventsWindow(const std::string &title, const calendar::TimePoint &dateFilter)
{
if (equivalentWindow == EquivalentWindow::DayEventsWindow) {
popToWindow(gui::name::window::main_window);
M module-apps/application-calendar/ApplicationCalendar.hpp => module-apps/application-calendar/ApplicationCalendar.hpp +2 -1
@@ 55,7 55,8 @@ namespace app
}
void createUserInterface() override;
void destroyUserInterface() override;
- void switchToNoEventsWindow(const std::string &title = "", const TimePoint &dateFilter = TimePoint());
+ void switchToNoEventsWindow(const std::string &title = "",
+ const calendar::TimePoint &dateFilter = calendar::TimePoint());
static const std::map<Reminder, const char *> reminderOptions;
static const std::map<Repeat, const char *> repeatOptions;
M module-apps/application-calendar/data/CalendarData.hpp => module-apps/application-calendar/data/CalendarData.hpp +3 -3
@@ 42,7 42,7 @@ class DayMonthData : public gui::SwitchData
{
protected:
std::string dayMonth;
- TimePoint dateFilter;
+ calendar::TimePoint dateFilter;
public:
DayMonthData() = default;
@@ 52,12 52,12 @@ class DayMonthData : public gui::SwitchData
return dayMonth;
};
- TimePoint getDateFilter()
+ calendar::TimePoint getDateFilter()
{
return dateFilter;
};
- virtual void setData(std::string dayMonthText, const TimePoint &dateNumb)
+ virtual void setData(std::string dayMonthText, const calendar::TimePoint &dateNumb)
{
dayMonth = dayMonthText;
dateFilter = dateNumb;
M module-apps/application-calendar/data/dateCommon.hpp => module-apps/application-calendar/data/dateCommon.hpp +35 -35
@@ 9,13 9,13 @@
#include <Utils.hpp>
#include <random>
-using namespace std::chrono;
-using namespace std::chrono_literals;
-
-using Clock = system_clock;
-using TimePoint = time_point<Clock>;
-using YearMonthDay = date::year_month_day;
-using YearMonthDayLast = date::year_month_day_last;
+namespace calendar
+{
+ using Clock = std::chrono::system_clock;
+ using TimePoint = std::chrono::time_point<Clock>;
+ using YearMonthDay = date::year_month_day;
+ using YearMonthDayLast = date::year_month_day_last;
+} // namespace calendar
inline constexpr auto max_month_day = 48;
@@ 43,7 43,7 @@ enum class Repeat
yearly
};
-inline constexpr TimePoint TIME_POINT_INVALID = date::sys_days{date::January / 1 / 1970};
+inline constexpr calendar::TimePoint TIME_POINT_INVALID = date::sys_days{date::January / 1 / 1970};
inline constexpr uint32_t yearDigitsNumb = 4, monthDigitsNumb = 2, dayDigitsNumb = 2, HourDigitsNumb = 2,
MinDigitsNumb = 2, SecDigitsNumb = 2;
@@ 88,34 88,34 @@ inline time_t GetAsUTCTime(int year, int month, int day, int hour = 0, int minut
return basetime + GetDiffLocalWithUTCTime();
}
-inline TimePoint TimePointFromTimeT(const time_t &time)
+inline calendar::TimePoint TimePointFromTimeT(const time_t &time)
{
- return system_clock::from_time_t(time);
+ return std::chrono::system_clock::from_time_t(time);
}
-inline time_t TimePointToTimeT(const TimePoint &tp)
+inline time_t TimePointToTimeT(const calendar::TimePoint &tp)
{
- return system_clock::to_time_t(tp);
+ return std::chrono::system_clock::to_time_t(tp);
}
-inline TimePoint TimePointNow()
+inline calendar::TimePoint TimePointNow()
{
utils::time::Timestamp timestamp;
return TimePointFromTimeT(timestamp.getTime());
}
-inline std::string TimePointToString(const TimePoint &tp)
+inline std::string TimePointToString(const calendar::TimePoint &tp)
{
- return date::format("%F %T", time_point_cast<seconds>(tp));
+ return date::format("%F %T", std::chrono::time_point_cast<std::chrono::seconds>(tp));
}
-inline auto TimePointToHourMinSec(const TimePoint &tp)
+inline auto TimePointToHourMinSec(const calendar::TimePoint &tp)
{
auto dp = date::floor<date::days>(tp);
return date::make_time(tp - dp);
}
-inline uint32_t TimePointToHour24H(const TimePoint &tp)
+inline uint32_t TimePointToHour24H(const calendar::TimePoint &tp)
{
auto time = TimePointToTimeT(tp);
utils::time::Timestamp timestamp(time);
@@ 123,7 123,7 @@ inline uint32_t TimePointToHour24H(const TimePoint &tp)
return hour;
}
-inline uint32_t TimePointToMinutes(const TimePoint &tp)
+inline uint32_t TimePointToMinutes(const calendar::TimePoint &tp)
{
auto time = TimePointToTimeT(tp);
utils::time::Timestamp timestamp(time);
@@ 131,7 131,7 @@ inline uint32_t TimePointToMinutes(const TimePoint &tp)
return minute;
}
-inline TimePoint getFirstWeekDay(const TimePoint &tp)
+inline calendar::TimePoint getFirstWeekDay(const calendar::TimePoint &tp)
{
date::year_month_day yearMonthDay = date::year_month_day{date::floor<date::days>(tp)};
auto hourV = TimePointToHour24H(tp);
@@ 146,12 146,12 @@ inline TimePoint getFirstWeekDay(const TimePoint &tp)
return finalDateTime;
}
-inline std::string TimePointToString(const TimePoint &tp, date::months months)
+inline std::string TimePointToString(const calendar::TimePoint &tp, date::months months)
{
date::year_month_day yearMonthDay = date::year_month_day{date::floor<date::days>(tp)};
date::year_month_day yearMonthDayLast = yearMonthDay.year() / yearMonthDay.month() / date::last;
- TimePoint timePoint;
+ calendar::TimePoint timePoint;
if ((static_cast<unsigned>(yearMonthDay.month()) + months.count()) <= 12) {
if (yearMonthDayLast.day() == yearMonthDay.day()) {
@@ 173,41 173,41 @@ inline std::string TimePointToString(const TimePoint &tp, date::months months)
timePoint = date::sys_days{yearMonthDay.year() / yearMonthDay.month() / yearMonthDay.day()};
}
}
- return date::format("%F %T", time_point_cast<seconds>(timePoint));
+ return date::format("%F %T", std::chrono::time_point_cast<std::chrono::seconds>(timePoint));
}
-inline std::string TimePointToLocalizedDateString(const TimePoint &tp, const std::string format = "")
+inline std::string TimePointToLocalizedDateString(const calendar::TimePoint &tp, const std::string format = "")
{
auto time = TimePointToTimeT(tp);
utils::time::Date timestamp(time);
return timestamp.str(format);
}
-inline std::string TimePointToLocalizedTimeString(const TimePoint &tp, const std::string format = "")
+inline std::string TimePointToLocalizedTimeString(const calendar::TimePoint &tp, const std::string format = "")
{
auto time = TimePointToTimeT(tp);
utils::time::Time timestamp(time);
return timestamp.str(format);
}
-inline TimePoint TimePointFromString(const char *s1)
+inline calendar::TimePoint TimePointFromString(const char *s1)
{
- TimePoint tp;
+ calendar::TimePoint tp;
std::istringstream(s1) >> date::parse("%F %T", tp);
return tp;
}
-inline YearMonthDay TimePointToYearMonthDay(const TimePoint &tp)
+inline calendar::YearMonthDay TimePointToYearMonthDay(const calendar::TimePoint &tp)
{
return date::year_month_day{date::floor<date::days>(tp)};
}
-inline TimePoint TimePointFromYearMonthDay(const YearMonthDay &ymd)
+inline calendar::TimePoint TimePointFromYearMonthDay(const calendar::YearMonthDay &ymd)
{
return date::sys_days{ymd.year() / ymd.month() / ymd.day()};
}
-inline time_t TimePointToMin(const TimePoint &tp)
+inline time_t TimePointToMin(const calendar::TimePoint &tp)
{
auto time = TimePointToTimeT(tp);
auto duration = new utils::time::Duration(time);
@@ 215,7 215,7 @@ inline time_t TimePointToMin(const TimePoint &tp)
return minutes;
}
-inline uint32_t TimePointToHour12H(const TimePoint &tp)
+inline uint32_t TimePointToHour12H(const calendar::TimePoint &tp)
{
auto time = TimePointToTimeT(tp);
utils::time::Timestamp timestamp(time);
@@ 226,7 226,7 @@ inline uint32_t TimePointToHour12H(const TimePoint &tp)
return hour;
}
-inline std::string TimePointToHourString12H(const TimePoint &tp)
+inline std::string TimePointToHourString12H(const calendar::TimePoint &tp)
{
auto hour =
utils::time::Timestamp(TimePointToTimeT(tp)).get_UTC_date_time_sub_value(utils::time::GetParameters::Hour);
@@ 234,14 234,14 @@ inline std::string TimePointToHourString12H(const TimePoint &tp)
return utils::to_string(hour12h);
}
-inline std::string TimePointToHourString24H(const TimePoint &tp)
+inline std::string TimePointToHourString24H(const calendar::TimePoint &tp)
{
auto hour =
utils::time::Timestamp(TimePointToTimeT(tp)).get_UTC_date_time_sub_value(utils::time::GetParameters::Hour);
return utils::to_string(hour);
}
-inline std::string TimePointToMinutesString(const TimePoint &tp)
+inline std::string TimePointToMinutesString(const calendar::TimePoint &tp)
{
auto minute = TimePointToMinutes(tp);
auto minuteString = std::to_string(minute);
@@ 252,9 252,9 @@ inline std::string TimePointToMinutesString(const TimePoint &tp)
}
// 0: Monday, 1: Tuesday ... 6: Sunday
-inline unsigned int WeekdayIndexFromTimePoint(const TimePoint &tp)
+inline unsigned int WeekdayIndexFromTimePoint(const calendar::TimePoint &tp)
{
- auto ymw = date::year_month_weekday{floor<date::days>(tp)};
+ auto ymw = date::year_month_weekday{std::chrono::floor<date::days>(tp)};
return ymw.weekday().iso_encoding() - 1;
}
M module-apps/application-calendar/models/AllEventsModel.cpp => module-apps/application-calendar/models/AllEventsModel.cpp +2 -2
@@ 83,8 83,8 @@ auto AllEventsModel::handleQueryResponse(db::QueryResult *queryResult) -> bool
auto eventShift = app->getEventShift();
if (eventShift) {
for (auto &record : records) {
- record.date_from += hours(eventShift);
- record.date_till += hours(eventShift);
+ record.date_from += std::chrono::hours(eventShift);
+ record.date_till += std::chrono::hours(eventShift);
}
}
return this->updateRecords(std::move(records));
M module-apps/application-calendar/models/DayEventsModel.cpp => module-apps/application-calendar/models/DayEventsModel.cpp +3 -3
@@ 82,8 82,8 @@ auto DayEventsModel::handleQueryResponse(db::QueryResult *queryResult) -> bool
auto eventShift = app->getEventShift();
if (eventShift) {
for (auto &record : records) {
- record.date_from += hours(eventShift);
- record.date_till += hours(eventShift);
+ record.date_from += std::chrono::hours(eventShift);
+ record.date_till += std::chrono::hours(eventShift);
}
}
return updateRecords(std::move(records));
@@ 95,7 95,7 @@ auto DayEventsModel::handleQueryResponse(db::QueryResult *queryResult) -> bool
return false;
}
-void DayEventsModel::setFilters(TimePoint from, TimePoint till, const std::string &dayMonth)
+void DayEventsModel::setFilters(calendar::TimePoint from, calendar::TimePoint till, const std::string &dayMonth)
{
this->filterFrom = from;
this->filterTill = till;
M module-apps/application-calendar/models/DayEventsModel.hpp => module-apps/application-calendar/models/DayEventsModel.hpp +3 -3
@@ 15,13 15,13 @@ class DayEventsModel : public app::DatabaseModel<EventsRecord>,
{
app::Application *application = nullptr;
std::string dayMonthTitle;
- TimePoint filterFrom = TIME_POINT_INVALID;
- TimePoint filterTill = TIME_POINT_INVALID;
+ calendar::TimePoint filterFrom = TIME_POINT_INVALID;
+ calendar::TimePoint filterTill = TIME_POINT_INVALID;
public:
DayEventsModel(app::Application *app);
- void setFilters(TimePoint from, TimePoint till, const std::string &dayMonth);
+ void setFilters(calendar::TimePoint from, calendar::TimePoint till, const std::string &dayMonth);
bool updateRecords(std::vector<EventsRecord> records) override;
auto handleQueryResponse(db::QueryResult *) -> bool;
M module-apps/application-calendar/widgets/EventDateItem.cpp => module-apps/application-calendar/widgets/EventDateItem.cpp +3 -3
@@ 149,7 149,7 @@ namespace gui
return true;
}
- YearMonthDay EventDateItem::validateDate()
+ calendar::YearMonthDay EventDateItem::validateDate()
{
auto actualDate = TimePointToYearMonthDay(TimePointNow());
uint32_t day;
@@ 185,7 185,7 @@ namespace gui
}
month = std::clamp(static_cast<unsigned>(month), 1u, static_cast<unsigned>(date::dec));
- YearMonthDayLast max_date = date::year(year) / date::month(month) / date::last;
+ calendar::YearMonthDayLast max_date = date::year(year) / date::month(month) / date::last;
if (day > static_cast<unsigned>(max_date.day())) {
dayInput->setText(std::to_string(static_cast<unsigned>(max_date.day())));
}
@@ 194,7 194,7 @@ namespace gui
return date::year(year) / date::month(month) / date::day(day);
}
- const YearMonthDay EventDateItem::getChosenDate()
+ const calendar::YearMonthDay EventDateItem::getChosenDate()
{
return validateDate();
}
M module-apps/application-calendar/widgets/EventDateItem.hpp => module-apps/application-calendar/widgets/EventDateItem.hpp +2 -2
@@ 24,12 24,12 @@ namespace gui
void buildInterface();
void applyItemSpecificProperties(gui::Text *item);
void applyCallbacks();
- YearMonthDay validateDate();
+ calendar::YearMonthDay validateDate();
public:
EventDateItem();
- const YearMonthDay getChosenDate();
+ const calendar::YearMonthDay getChosenDate();
// virtual methods from Item
bool onDimensionChanged(const BoundingBox &oldDim, const BoundingBox &newDim) override;
};
M module-apps/application-calendar/widgets/EventTimeItem.cpp => module-apps/application-calendar/widgets/EventTimeItem.cpp +3 -3
@@ 433,9 433,9 @@ namespace gui
}
}
- TimePoint EventTimeItem::calculateEventTime(YearMonthDay date,
- std::chrono::hours hours,
- std::chrono::minutes minutes)
+ calendar::TimePoint EventTimeItem::calculateEventTime(calendar::YearMonthDay date,
+ std::chrono::hours hours,
+ std::chrono::minutes minutes)
{
return TimePointFromYearMonthDay(date) + hours + minutes;
}
M module-apps/application-calendar/widgets/EventTimeItem.hpp => module-apps/application-calendar/widgets/EventTimeItem.hpp +3 -1
@@ 43,7 43,9 @@ namespace gui
std::chrono::minutes end_hour,
uint32_t start_minutes,
uint32_t end_minutes);
- TimePoint calculateEventTime(YearMonthDay date, std::chrono::hours hours, std::chrono::minutes minutes);
+ calendar::TimePoint calculateEventTime(calendar::YearMonthDay date,
+ std::chrono::hours hours,
+ std::chrono::minutes minutes);
public:
EventTimeItem(const std::string &description,
M module-apps/application-calendar/widgets/MonthBox.cpp => module-apps/application-calendar/widgets/MonthBox.cpp +1 -1
@@ 58,7 58,7 @@ namespace gui
auto mainWindow = dynamic_cast<CalendarMainWindow *>(parent);
if (mainWindow->returnedFromWindow) {
focusChangedCallback = [=](Item &item) {
- YearMonthDay date = monthFilterValue.year() / monthFilterValue.month() / date::last;
+ calendar::YearMonthDay date = monthFilterValue.year() / monthFilterValue.month() / date::last;
if (unsigned(date.day()) < mainWindow->dayFocusedBefore) {
setFocusOnElement(unsigned(date.day()) - 1);
}
M module-apps/application-calendar/windows/AllEventsWindow.cpp => module-apps/application-calendar/windows/AllEventsWindow.cpp +0 -1
@@ 34,7 34,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
bottomBar->setText(gui::BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
M module-apps/application-calendar/windows/AllEventsWindow.hpp => module-apps/application-calendar/windows/AllEventsWindow.hpp +1 -1
@@ 16,7 16,7 @@ namespace gui
gui::Image *leftArrowImage = nullptr;
gui::Image *newDayEventImage = nullptr;
- TimePoint dateFilter = TimePointNow();
+ calendar::TimePoint dateFilter = TimePointNow();
gui::ListView *allEventsList = nullptr;
std::shared_ptr<AllEventsModel> allEventsModel = nullptr;
M module-apps/application-calendar/windows/CalendarMainWindow.cpp => module-apps/application-calendar/windows/CalendarMainWindow.cpp +8 -8
@@ 100,9 100,9 @@ namespace gui
}
case KeyCode::KEY_LEFT: {
LOG_DEBUG("Call borderCallback -> go to the previous element");
- auto it = monthBox->getNavigationFocusedItem();
- if (monthBox->nextNavigationItem(std::prev(it)) != nullptr) {
- monthBox->setFocusItem(monthBox->nextNavigationItem(std::prev(it)));
+ auto it = std::prev(monthBox->getNavigationFocusedItem());
+ if (it != monthBox->children.end() && (*it)->isActive()) {
+ monthBox->setFocusItem(*it);
}
else {
monthBox->setFocusOnLastElement();
@@ 111,9 111,9 @@ namespace gui
}
case KeyCode::KEY_RIGHT: {
LOG_DEBUG("Call borderCallback -> go to the next element");
- auto it = monthBox->getNavigationFocusedItem();
- if (monthBox->nextNavigationItem(std::next(it)) != nullptr) {
- monthBox->setFocusItem(monthBox->nextNavigationItem(std::next(it)));
+ auto it = std::next(monthBox->getNavigationFocusedItem());
+ if (it != monthBox->children.end() && (*it)->isActive()) {
+ monthBox->setFocusItem(*it);
}
else {
monthBox->setFocusOnElement(0);
@@ 197,8 197,8 @@ namespace gui
void CalendarMainWindow::filterRequest()
{
- YearMonthDay date_from = actualDate.year() / actualDate.month() / 1;
- YearMonthDay date_till = date_from + date::months{1};
+ calendar::YearMonthDay date_from = actualDate.year() / actualDate.month() / 1;
+ calendar::YearMonthDay date_till = date_from + date::months{1};
auto filter_from = TimePointFromYearMonthDay(date_from);
auto filter_till = TimePointFromYearMonthDay(date_till);
LOG_DEBUG("filter: %s", TimePointToString(filter_till).c_str());
M module-apps/application-calendar/windows/CustomRepeatWindow.cpp => module-apps/application-calendar/windows/CustomRepeatWindow.cpp +0 -1
@@ 28,7 28,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-calendar/windows/DayEventsWindow.cpp => module-apps/application-calendar/windows/DayEventsWindow.cpp +0 -1
@@ 64,7 64,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
bottomBar->setText(gui::BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
M module-apps/application-calendar/windows/DayEventsWindow.hpp => module-apps/application-calendar/windows/DayEventsWindow.hpp +1 -1
@@ 19,7 19,7 @@ namespace gui
class DayEventsWindow : public gui::AppWindow
{
std::string dayMonthTitle;
- TimePoint filterFrom;
+ calendar::TimePoint filterFrom;
gui::Image *leftArrowImage = nullptr;
gui::Image *newDayEventImage = nullptr;
gui::ListView *dayEventsList = nullptr;
M module-apps/application-calendar/windows/EventDetailWindow.cpp => module-apps/application-calendar/windows/EventDetailWindow.cpp +0 -1
@@ 28,7 28,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setActive(gui::BottomBar::Side::LEFT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-calendar/windows/EventReminderWindow.cpp => module-apps/application-calendar/windows/EventReminderWindow.cpp +11 -4
@@ 38,14 38,21 @@ namespace gui
buildInterface();
}
+ top_bar::Configuration EventReminderWindow::configureTopBar(top_bar::Configuration appConfiguration)
+ {
+ using namespace top_bar;
+ appConfiguration.enable({Indicator::Signal,
+ Indicator::Time,
+ Indicator::Battery,
+ Indicator::SimCard,
+ Indicator::NetworkAccessTechnology});
+ return appConfiguration;
+ }
+
void EventReminderWindow::buildInterface()
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::BATTERY, true);
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(gui::TopBar::Elements::TIME, true);
-
bottomBar->setActive(gui::BottomBar::Side::CENTER, true);
bottomBar->setText(gui::BottomBar::Side::CENTER, utils::localize.get(style::strings::common::ok));
bottomBar->setBorderColor(ColorNoColor);
M module-apps/application-calendar/windows/EventReminderWindow.hpp => module-apps/application-calendar/windows/EventReminderWindow.hpp +1 -0
@@ 42,6 42,7 @@ namespace gui
void rebuild() override;
void buildInterface() override;
void destroyInterface() override;
+ top_bar::Configuration configureTopBar(top_bar::Configuration appConfiguration) override;
auto handleSwitchData(SwitchData *data) -> bool override;
};
M module-apps/application-calendar/windows/NewEditEventWindow.cpp => module-apps/application-calendar/windows/NewEditEventWindow.cpp +0 -1
@@ 25,7 25,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::TIME, true);
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setActive(gui::BottomBar::Side::CENTER, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-call/ApplicationCall.cpp => module-apps/application-call/ApplicationCall.cpp +6 -0
@@ 33,6 33,12 @@ namespace app
ApplicationCall::ApplicationCall(std::string name, std::string parent, StartInBackground startInBackground)
: Application(name, parent, startInBackground, app::call_stack_size)
{
+ using namespace gui::top_bar;
+ topBarManager->enableIndicators({Indicator::Signal,
+ Indicator::Time,
+ Indicator::Battery,
+ Indicator::SimCard,
+ Indicator::NetworkAccessTechnology});
addActionReceiver(manager::actions::Call, [this](auto &&data) {
switchWindow(window::name_call, std::forward<decltype(data)>(data));
return msgHandled();
M module-apps/application-call/windows/CallWindow.cpp => module-apps/application-call/windows/CallWindow.cpp +0 -4
@@ 58,10 58,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(gui::TopBar::Elements::BATTERY, true);
- topBar->setActive(gui::TopBar::Elements::SIGNAL, true);
- topBar->setActive(gui::TopBar::Elements::TIME, true);
-
bottomBar->setActive(BottomBar::Side::CENTER, true);
bottomBar->setActive(BottomBar::Side::RIGHT, true);
M module-apps/application-call/windows/EnterNumberWindow.cpp => module-apps/application-call/windows/EnterNumberWindow.cpp +0 -4
@@ 58,10 58,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get("common_add"));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get("app_call_clear"));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
- topBar->setActive(TopBar::Elements::TIME, true);
-
numberLabel = new gui::Label(this, numberLabel::x, numberLabel::y, numberLabel::w, numberLabel::h);
numberLabel->setPenWidth(numberLabel::borderW);
numberLabel->setFont(style::window::font::largelight);
M module-apps/application-calllog/windows/CallLogDetailsWindow.cpp => module-apps/application-calllog/windows/CallLogDetailsWindow.cpp +0 -2
@@ 82,8 82,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::call));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::TIME, true);
-
// NOTE: height of all labels is set using decorators
// Information
M module-apps/application-calllog/windows/CallLogMainWindow.cpp => module-apps/application-calllog/windows/CallLogMainWindow.cpp +0 -2
@@ 47,8 47,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::TIME, true);
-
list = new gui::ListView(this, mainWindow::x, mainWindow::y, mainWindow::w, mainWindow::h, calllogModel);
setFocusItem(list);
M module-apps/application-desktop/ApplicationDesktop.cpp => module-apps/application-desktop/ApplicationDesktop.cpp +15 -4
@@ 37,6 37,12 @@ namespace app
ApplicationDesktop::ApplicationDesktop(std::string name, std::string parent, StartInBackground startInBackground)
: Application(name, parent, startInBackground), lockHandler(this)
{
+ using namespace gui::top_bar;
+ topBarManager->enableIndicators({Indicator::Signal,
+ Indicator::Time,
+ Indicator::Battery,
+ Indicator::SimCard,
+ Indicator::NetworkAccessTechnology});
busChannels.push_back(sys::BusChannels::ServiceDBNotifications);
addActionReceiver(app::manager::actions::RequestPin, [this](auto &&data) {
@@ 317,11 323,15 @@ namespace app
std::make_shared<sdesktop::UpdateOsMessage>(updateos::UpdateMessageType::UpdateCheckForUpdateOnce);
sys::Bus::SendUnicast(msgToSend, service::name::service_desktop, this);
- settings->registerValueChange(settings::SystemProperties::activeSim,
- [this](std::string value) { activeSimChanged(value); });
+ settings->registerValueChange(
+ settings::SystemProperties::activeSim,
+ [this](std::string value) { activeSimChanged(value); },
+ settings::SettingsScope::Global);
Store::GSM::get()->selected = Store::GSM::SIM::NONE;
- settings->registerValueChange(settings::SystemProperties::lockPassHash,
- [this](std::string value) { lockPassHashChanged(value); });
+ settings->registerValueChange(
+ settings::SystemProperties::lockPassHash,
+ [this](std::string value) { lockPassHashChanged(value); },
+ settings::SettingsScope::Global);
return sys::ReturnCodes::Success;
}
@@ 329,6 339,7 @@ namespace app
sys::ReturnCodes ApplicationDesktop::DeinitHandler()
{
LOG_INFO("DeinitHandler");
+ settings->unregisterValueChange();
return sys::ReturnCodes::Success;
}
M module-apps/application-desktop/data/Style.hpp => module-apps/application-desktop/data/Style.hpp +2 -2
@@ 24,7 24,7 @@ namespace style::desktop
constexpr auto X = 0;
constexpr auto Y = 106;
constexpr auto Width = style::window_width;
- constexpr auto Hight = 96;
+ constexpr auto Height = 96;
} // namespace timeLabel
@@ 33,7 33,7 @@ namespace style::desktop
constexpr auto X = 0;
constexpr auto Y = 204;
constexpr auto Width = style::window_width;
- constexpr auto Hight = 51;
+ constexpr auto Height = 51;
} // namespace dayLabel
M module-apps/application-desktop/windows/DesktopMainWindow.cpp => module-apps/application-desktop/windows/DesktopMainWindow.cpp +22 -8
@@ 35,19 35,17 @@ namespace gui
AppWindow::buildInterface();
bottomBar->setActive(BottomBar::Side::CENTER, true);
- topBar->setActive(
- {{TopBar::Elements::SIGNAL, true}, {TopBar::Elements::LOCK, true}, {TopBar::Elements::BATTERY, true}});
using namespace style::desktop;
- time = new gui::Label(this, timeLabel::X, timeLabel::Y, timeLabel::Width, timeLabel::Hight);
+ time = new gui::Label(this, timeLabel::X, timeLabel::Y, timeLabel::Width, timeLabel::Height);
time->setFilled(false);
time->setBorderColor(gui::ColorNoColor);
time->setFont(style::window::font::supersizemelight);
time->setText(ttime);
time->setAlignment(Alignment(gui::Alignment::Horizontal::Center, gui::Alignment::Vertical::Top));
- dayText = new gui::Label(this, dayLabel::X, dayLabel::Y, dayLabel::Width, dayLabel::Hight);
+ dayText = new gui::Label(this, dayLabel::X, dayLabel::Y, dayLabel::Width, dayLabel::Height);
dayText->setFilled(false);
dayText->setBorderColor(gui::ColorNoColor);
dayText->setFont(style::window::font::biglight);
@@ 75,6 73,20 @@ namespace gui
notifications = nullptr;
}
+ top_bar::Configuration DesktopMainWindow::configureTopBar(top_bar::Configuration appConfiguration)
+ {
+ auto app = getAppDesktop();
+ const auto isLocked = app->lockHandler.isScreenLocked();
+ updateTopBarConfiguration(isLocked, appConfiguration);
+ return appConfiguration;
+ }
+
+ void DesktopMainWindow::updateTopBarConfiguration(bool isScreenLocked, top_bar::Configuration &configuration)
+ {
+ configuration.set(top_bar::Indicator::Lock, isScreenLocked);
+ configuration.set(top_bar::Indicator::Time, !isScreenLocked);
+ }
+
DesktopMainWindow::DesktopMainWindow(app::Application *app) : AppWindow(app, app::window::name::desktop_main_window)
{
buildInterface();
@@ 89,13 101,18 @@ namespace gui
void DesktopMainWindow::setVisibleState()
{
auto app = getAppDesktop();
+ applyToTopBar([isLocked = app->lockHandler.isScreenLocked()](top_bar::Configuration configuration) {
+ updateTopBarConfiguration(isLocked, configuration);
+ return configuration;
+ });
+
if (app->lockHandler.isScreenLocked()) {
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get("app_desktop_unlock"));
bottomBar->setActive(BottomBar::Side::RIGHT, false);
bottomBar->setText(BottomBar::Side::LEFT,
utils::localize.get("app_desktop_emergency"),
app->lockHandler.isScreenBlocked());
- topBar->setActive(TopBar::Elements::LOCK, true);
+
inputCallback = nullptr;
setFocusItem(nullptr);
buildNotifications(app);
@@ 104,8 121,6 @@ namespace gui
std::make_shared<TimersProcessingStopMessage>(), service::name::service_time, application);
}
else {
- topBar->setActive(TopBar::Elements::LOCK, false);
-
if (!buildNotifications(app)) {
LOG_ERROR("Couldn't fit in all notifications");
}
@@ 146,7 161,6 @@ namespace gui
if (inputEvent.is(KeyCode::KEY_PND)) {
app->lockHandler.lockScreen();
setVisibleState();
- application->setSuspendFlag(true);
return true;
}
// long press of '0' key is translated to '+'
M module-apps/application-desktop/windows/DesktopMainWindow.hpp => module-apps/application-desktop/windows/DesktopMainWindow.hpp +3 -0
@@ 81,11 81,14 @@ namespace gui
void rebuild() override;
void buildInterface() override;
void destroyInterface() override;
+ top_bar::Configuration configureTopBar(top_bar::Configuration appConfiguration) override;
+
bool updateTime(const UTF8 &timeStr) override;
bool updateTime(const uint32_t ×tamp, bool mode24H) override;
private:
void invalidate() noexcept;
+ static void updateTopBarConfiguration(bool isScreenLocked, top_bar::Configuration &configuration);
gui::KeyInputMappedTranslation translator;
};
M module-apps/application-desktop/windows/LockWindow.cpp => module-apps/application-desktop/windows/LockWindow.cpp +0 -1
@@ 14,7 14,6 @@ namespace gui
void LockWindow::build()
{
buildBottomBar();
- buildTopBar();
buildTitleBar();
buildInfoTexts();
}
M module-apps/application-desktop/windows/LockWindow.hpp => module-apps/application-desktop/windows/LockWindow.hpp +0 -1
@@ 58,7 58,6 @@ namespace gui
protected:
virtual void buildBottomBar();
virtual void buildTitleBar() = 0;
- virtual void buildTopBar() = 0;
private:
[[nodiscard]] auto getText(TextType type) noexcept -> gui::Text *;
M module-apps/application-desktop/windows/LockedInfoWindow.cpp => module-apps/application-desktop/windows/LockedInfoWindow.cpp +7 -4
@@ 34,10 34,6 @@ void LockedInfoWindow::setVisibleState()
bottomBar->setActive(BottomBar::Side::LEFT, true);
bottomBar->setActive(BottomBar::Side::CENTER, false);
bottomBar->setActive(BottomBar::Side::RIGHT, true);
-
- topBar->setActive(TopBar::Elements::LOCK, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
- topBar->setActive(TopBar::Elements::SIGNAL, true);
}
bool LockedInfoWindow::onInput(const InputEvent &inputEvent)
@@ 61,6 57,13 @@ void LockedInfoWindow::rebuild()
buildInterface();
}
+top_bar::Configuration LockedInfoWindow::configureTopBar(top_bar::Configuration appConfiguration)
+{
+ appConfiguration.enable(top_bar::Indicator::Lock);
+ appConfiguration.disable(top_bar::Indicator::Time);
+ return appConfiguration;
+}
+
void LockedInfoWindow::buildInterface()
{
namespace lock_style = style::window::pin_lock;
M module-apps/application-desktop/windows/LockedInfoWindow.hpp => module-apps/application-desktop/windows/LockedInfoWindow.hpp +1 -0
@@ 25,5 25,6 @@ namespace gui
void rebuild() override;
void buildInterface() override;
void destroyInterface() override;
+ top_bar::Configuration configureTopBar(top_bar::Configuration appConfiguration) override;
};
} /* namespace gui */
M => +0 -3
@@ 149,9 149,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
topBar->setActive(TopBar::Elements::SIGNAL, true);
topBar->setActive(TopBar::Elements::BATTERY, true);
auto app = dynamic_cast<app::ApplicationDesktop *>(application);
assert(app);
M module-apps/application-desktop/windows/MmiPullWindow.cpp => module-apps/application-desktop/windows/MmiPullWindow.cpp +0 -2
@@ 37,8 37,6 @@ MmiPullWindow::MmiPullWindow(app::Application *app, const std::string &name) : g
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
- topBar->setActive(TopBar::Elements::SIM, false);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get("app_desktop_replay"));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
text = new Text(
M module-apps/application-desktop/windows/MmiPushWindow.cpp => module-apps/application-desktop/windows/MmiPushWindow.cpp +0 -2
@@ 30,8 30,6 @@ namespace style::desktop
MmiPushWindow::MmiPushWindow(app::Application *app, const std::string &name) : gui::AppWindow(app, name)
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
- topBar->setActive(TopBar::Elements::SIM, false);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::ok));
icon = new Image(this, style::desktop::image::x, style::desktop::image::y, "");
icon->set("info_big_circle_W_G");
M module-apps/application-desktop/windows/PinLockBaseWindow.cpp => module-apps/application-desktop/windows/PinLockBaseWindow.cpp +6 -7
@@ 32,7 32,12 @@ namespace gui
}
return std::string{};
}
-
+ top_bar::Configuration PinLockBaseWindow::configureTopBar(top_bar::Configuration appConfiguration)
+ {
+ appConfiguration.enable(top_bar::Indicator::Lock);
+ appConfiguration.disable(top_bar::Indicator::Time);
+ return appConfiguration;
+ }
void PinLockBaseWindow::restore() noexcept
{
LockWindow::restore();
@@ 91,10 96,4 @@ namespace gui
title->setPenWidth(2);
}
- void PinLockBaseWindow::buildTopBar()
- {
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
- topBar->setActive(TopBar::Elements::LOCK, true);
- }
} // namespace gui
M module-apps/application-desktop/windows/PinLockBaseWindow.hpp => module-apps/application-desktop/windows/PinLockBaseWindow.hpp +3 -1
@@ 12,6 12,9 @@ namespace gui
public:
PinLockBaseWindow(app::Application *app, std::string name) : LockWindow(app, name)
{}
+
+ top_bar::Configuration configureTopBar(top_bar::Configuration appConfiguration) override;
+
void buildImages(const std::string &lockImg, const std::string &infoImg);
[[nodiscard]] auto getToken(Token token) const -> std::string;
void restore() noexcept override;
@@ 25,6 28,5 @@ namespace gui
private:
void buildBottomBar() override;
void buildTitleBar() override;
- void buildTopBar() override;
};
} // namespace gui
M module-apps/application-meditation/windows/MeditationListViewWindows.cpp => module-apps/application-meditation/windows/MeditationListViewWindows.cpp +0 -2
@@ 64,7 64,6 @@ void MeditationOptionsWindow::buildInterface()
MeditationListViewWindow::buildInterface();
setTitle(utils::localize.get("common_options"));
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::Switch));
- topBar->setActive(TopBar::Elements::TIME, true);
}
PreparationTimeWindow::PreparationTimeWindow(app::Application *app)
@@ 79,5 78,4 @@ void PreparationTimeWindow::buildInterface()
MeditationListViewWindow::buildInterface();
setTitle(utils::localize.get("app_meditation_preparation_time"));
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
- topBar->setActive(TopBar::Elements::TIME, true);
}
M module-apps/application-meditation/windows/MeditationTimerWindow.cpp => module-apps/application-meditation/windows/MeditationTimerWindow.cpp +5 -1
@@ 112,7 112,11 @@ auto MeditationTimerWindow::onInput(const InputEvent &inputEvent) -> bool
void MeditationTimerWindow::setWidgetVisible(bool tBar, bool bBar, bool counter)
{
- topBar->setActive(TopBar::Elements::TIME, tBar);
+ applyToTopBar([tBar](top_bar::Configuration configuration) {
+ configuration.set(top_bar::Indicator::Time, tBar);
+ return configuration;
+ });
+
title->setVisible(tBar);
bottomBar->setActive(BottomBar::Side::CENTER, bBar);
bottomBar->setActive(BottomBar::Side::LEFT, bBar);
M module-apps/application-messages/windows/MessagesMainWindow.cpp => module-apps/application-messages/windows/MessagesMainWindow.cpp +0 -2
@@ 64,8 64,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::open));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::TIME, true);
-
setTitle(utils::localize.get("app_messages_title_main"));
leftArrowImage = new gui::Image(this, 30, 62, 0, 0, "arrow_left");
M module-apps/application-messages/windows/NewMessage.cpp => module-apps/application-messages/windows/NewMessage.cpp +0 -3
@@ 188,9 188,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get(style::strings::common::options));
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
- topBar->setActive(TopBar::Elements::SIGNAL, false);
setTitle(utils::localize.get("sms_title_message"));
M module-apps/application-messages/windows/SMSTemplatesWindow.cpp => module-apps/application-messages/windows/SMSTemplatesWindow.cpp +0 -2
@@ 44,8 44,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::use));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::TIME, true);
-
namespace style = style::messages::templates::list;
list = new gui::ListView(this, style::x, style::y, style::w, style::h, smsTemplateModel);
M module-apps/application-messages/windows/SMSThreadViewWindow.cpp => module-apps/application-messages/windows/SMSThreadViewWindow.cpp +0 -1
@@ 29,7 29,6 @@ namespace gui
{
AppWindow::buildInterface();
setTitle(utils::localize.get("app_messages_title_main"));
- topBar->setActive(TopBar::Elements::TIME, true);
bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get(style::strings::common::options));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-music-player/windows/MusicPlayerAllSongsWindow.cpp => module-apps/application-music-player/windows/MusicPlayerAllSongsWindow.cpp +0 -2
@@ 54,8 54,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get("app_music_player_play"));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::TIME, true);
-
songsList = new gui::ListView(this,
musicPlayerStyle::allSongsWindow::x,
musicPlayerStyle::allSongsWindow::y,
M module-apps/application-music-player/windows/MusicPlayerEmptyWindow.cpp => module-apps/application-music-player/windows/MusicPlayerEmptyWindow.cpp +0 -2
@@ 33,8 33,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get("app_music_player_music_library"));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get("app_music_player_quit"));
- topBar->setActive(TopBar::Elements::TIME, true);
-
img = new gui::Image(this, noteImg::x, noteImg::y, "note");
text = new Text(this, infoText::x, infoText::y, infoText::w, infoText::h);
M module-apps/application-notes/windows/NoteEditWindow.cpp => module-apps/application-notes/windows/NoteEditWindow.cpp +0 -2
@@ 85,8 85,6 @@ namespace app::notes
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(::style::strings::common::back));
- topBar->setActive(gui::TopBar::Elements::TIME, true);
-
setFocusItem(edit);
}
M module-apps/application-notes/windows/NoteMainWindow.cpp => module-apps/application-notes/windows/NoteMainWindow.cpp +0 -1
@@ 54,7 54,6 @@ namespace app::notes
bottomBar->setText(gui::BottomBar::Side::CENTER, utils::localize.get(::style::strings::common::open));
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(::style::strings::common::back));
- topBar->setActive(gui::TopBar::Elements::TIME, true);
namespace windowStyle = app::notes::style::main_window;
leftArrowImage = new gui::Image(this,
M module-apps/application-notes/windows/NotePreviewWindow.cpp => module-apps/application-notes/windows/NotePreviewWindow.cpp +0 -2
@@ 79,8 79,6 @@ namespace app::notes
bottomBar->setActive(gui::BottomBar::Side::RIGHT, true);
bottomBar->setText(gui::BottomBar::Side::RIGHT, utils::localize.get(::style::strings::common::back));
- topBar->setActive(gui::TopBar::Elements::TIME, true);
-
setFocusItem(note);
}
M module-apps/application-phonebook/windows/PhonebookContactDetails.cpp => module-apps/application-phonebook/windows/PhonebookContactDetails.cpp +0 -1
@@ 25,7 25,6 @@ namespace gui
void PhonebookContactDetails::buildInterface()
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get(style::strings::common::options));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
M module-apps/application-phonebook/windows/PhonebookIceContacts.cpp => module-apps/application-phonebook/windows/PhonebookIceContacts.cpp +0 -1
@@ 25,7 25,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
setTitle(utils::localize.get("app_phonebook_ice_contacts_title"));
contactsListIce = new gui::ListView(this,
M module-apps/application-phonebook/windows/PhonebookMainWindow.cpp => module-apps/application-phonebook/windows/PhonebookMainWindow.cpp +0 -1
@@ 30,7 30,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
setTitle(utils::localize.get("app_phonebook_title_main"));
leftArrowImage = new gui::Image(this,
phonebookStyle::mainWindow::leftArrowImage::x,
M module-apps/application-phonebook/windows/PhonebookSearch.cpp => module-apps/application-phonebook/windows/PhonebookSearch.cpp +0 -1
@@ 16,7 16,6 @@ namespace gui
void PhonebookSearch::buildInterface()
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
setTitle(utils::localize.get("app_phonebook_title_main"));
M module-apps/application-phonebook/windows/PhonebookSearchResults.cpp => module-apps/application-phonebook/windows/PhonebookSearchResults.cpp +0 -2
@@ 40,8 40,6 @@ namespace gui
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::TIME, true);
-
setTitle(utils::localize.get("common_results_prefix"));
}
M module-apps/application-settings-new/ApplicationSettings.cpp => module-apps/application-settings-new/ApplicationSettings.cpp +101 -24
@@ 5,7 5,8 @@
#include "windows/AddDeviceWindow.hpp"
#include "windows/AllDevicesWindow.hpp"
-#include "windows/APNSettingsWindow.hpp"
+#include "windows/ApnSettingsWindow.hpp"
+#include "windows/ApnOptionsWindow.hpp"
#include "windows/BluetoothWindow.hpp"
#include "windows/SettingsMainWindow.hpp"
#include "windows/DisplayAndKeypadWindow.hpp"
@@ 25,28 26,38 @@
#include "windows/QuotesMainWindow.hpp"
#include "windows/QuotesAddWindow.hpp"
#include "windows/SecurityMainWindow.hpp"
+#include "windows/QuotesOptionsWindow.hpp"
#include "windows/ChangePasscodeWindow.hpp"
+#include "windows/SystemMainWindow.hpp"
+#include "windows/NewApnWindow.hpp"
#include "Dialog.hpp"
#include <service-evtmgr/EventManagerServiceAPI.hpp>
-#include <service-bluetooth/BluetoothMessage.hpp>
#include <service-cellular/CellularServiceAPI.hpp>
-#include <service-db/Settings.hpp>
-#include <module-services/service-bluetooth/service-bluetooth/messages/Status.hpp>
+#include <service-bluetooth/BluetoothMessage.hpp>
+#include <service-bluetooth/service-bluetooth/messages/Status.hpp>
#include <service-bluetooth/messages/BondedDevices.hpp>
#include <service-bluetooth/messages/DeviceName.hpp>
-#include <application-settings-new/data/BondedDevicesData.hpp>
#include <service-db/agents/settings/SystemSettings.hpp>
+#include <application-settings-new/data/ApnListData.hpp>
+#include <application-settings-new/data/BondedDevicesData.hpp>
#include <application-settings-new/data/PhoneNameData.hpp>
#include <module-services/service-db/agents/settings/SystemSettings.hpp>
+#include <service-db/Settings.hpp>
+
+#include <i18n/i18n.hpp>
+#include <module-services/service-evtmgr/service-evtmgr/ScreenLightControlMessage.hpp>
+#include <module-services/service-evtmgr/service-evtmgr/Constants.hpp>
namespace app
{
namespace settings
{
constexpr inline auto operators_on = "operators_on";
- }
+ const std::string quotesPath =
+ purefs::createPath(purefs::dir::getUserDiskPath(), "data/applications/settings/quotes.json");
+ } // namespace settings
ApplicationSettingsNew::ApplicationSettingsNew(std::string name,
std::string parent,
@@ 57,17 68,10 @@ namespace app
Store::GSM::get()->sim == selectedSim) {
selectedSimNumber = CellularServiceAPI::GetOwnNumber(this);
}
- settings->registerValueChange(settings::operators_on,
- [this](const std::string &value) { operatorOnChanged(value); });
-
- settings->registerValueChange(::settings::Cellular::volte_on,
- [this](const std::string &value) { volteChanged(value); });
}
ApplicationSettingsNew::~ApplicationSettingsNew()
{
- settings->unregisterValueChange(settings::operators_on);
- settings->unregisterValueChange(::settings::Cellular::volte_on);
}
// Invoked upon receiving data message
@@ 143,13 147,29 @@ namespace app
return sys::MessageNone{};
});
+ connect(typeid(CellularGetAPNResponse), [&](sys::Message *msg) {
+ if (gui::window::name::apn_settings == getCurrentWindow()->getName()) {
+ auto apns = dynamic_cast<CellularGetAPNResponse *>(msg);
+ if (apns != nullptr) {
+ auto apnsData = std::make_unique<gui::ApnListData>(apns->getAPNs());
+ switchWindow(gui::window::name::apn_settings, std::move(apnsData));
+ }
+ }
+ return sys::MessageNone{};
+ });
+
createUserInterface();
setActiveWindow(gui::name::window::main_window);
- settings->registerValueChange(::settings::SystemProperties::lockPassHash, [this](std::string value) {
- lockPassHash = utils::getNumericValue<unsigned int>(value);
- });
+ settings->registerValueChange(settings::operators_on,
+ [this](const std::string &value) { operatorOnChanged(value); });
+ settings->registerValueChange(::settings::Cellular::volte_on,
+ [this](const std::string &value) { volteChanged(value); });
+ settings->registerValueChange(
+ ::settings::SystemProperties::lockPassHash,
+ [this](std::string value) { lockPassHash = utils::getNumericValue<unsigned int>(value); },
+ ::settings::SettingsScope::Global);
return ret;
}
@@ 188,7 208,7 @@ namespace app
return std::make_unique<gui::FontSizeWindow>(app);
});
windowsFactory.attach(gui::window::name::display_light, [](Application *app, const std::string &name) {
- return std::make_unique<gui::DisplayLightWindow>(app);
+ return std::make_unique<gui::DisplayLightWindow>(app, static_cast<ApplicationSettingsNew *>(app));
});
windowsFactory.attach(gui::window::name::apps_and_tools, [](Application *app, const std::string &name) {
return std::make_unique<gui::AppsAndToolsWindow>(app);
@@ 201,7 221,10 @@ namespace app
app, static_cast<ApplicationSettingsNew *>(app), static_cast<ApplicationSettingsNew *>(app));
});
windowsFactory.attach(gui::window::name::apn_settings, [](Application *app, const std::string &name) {
- return std::make_unique<gui::APNSettingsWindow>(app);
+ return std::make_unique<gui::ApnSettingsWindow>(app);
+ });
+ windowsFactory.attach(gui::window::name::apn_options, [](Application *app, const std::string &name) {
+ return std::make_unique<gui::ApnOptionsWindow>(app);
});
windowsFactory.attach(gui::window::name::messages, [](Application *app, const std::string &name) {
return std::make_unique<gui::MessagesWindow>(app);
@@ 218,11 241,8 @@ namespace app
windowsFactory.attach(gui::window::name::wallpaper, [](Application *app, const std::string &name) {
return std::make_unique<gui::WallpaperWindow>(app);
});
- windowsFactory.attach(gui::window::name::quotes, [](Application *app, const std::string &name) {
- return std::make_unique<gui::QuotesMainWindow>(app);
- });
- windowsFactory.attach(gui::window::name::new_quote, [](Application *app, const std::string &name) {
- return std::make_unique<gui::QuotesAddWindow>(app);
+ windowsFactory.attach(gui::window::name::quotes_dialog_yes_no, [](Application *app, const std::string &name) {
+ return std::make_unique<gui::DialogYesNo>(app, name);
});
windowsFactory.attach(gui::window::name::security, [](Application *app, const std::string &name) {
return std::make_unique<gui::SecurityMainWindow>(app);
@@ 233,6 253,12 @@ namespace app
windowsFactory.attach(gui::window::name::dialog_confirm, [](Application *app, const std::string &name) {
return std::make_unique<gui::DialogConfirm>(app, gui::window::name::dialog_confirm);
});
+ windowsFactory.attach(gui::window::name::system, [](Application *app, const std::string &name) {
+ return std::make_unique<gui::SystemMainWindow>(app);
+ });
+ windowsFactory.attach(gui::window::name::new_apn, [](Application *app, const std::string &name) {
+ return std::make_unique<gui::NewApnWindow>(app);
+ });
}
void ApplicationSettingsNew::destroyUserInterface()
@@ 255,17 281,20 @@ namespace app
void ApplicationSettingsNew::operatorOnChanged(const std::string &value)
{
+ LOG_DEBUG("[ApplicationSettingsNew::operatorOnChanged] value=%s", value.c_str());
if (!value.empty()) {
operatorsOn = utils::getNumericValue<bool>(value);
}
}
bool ApplicationSettingsNew::getOperatorsOn() const noexcept
{
+ LOG_DEBUG("[ApplicationSettingsNew::getOperatorsOn] %d", operatorsOn);
return operatorsOn;
}
void ApplicationSettingsNew::setOperatorsOn(bool value)
{
operatorsOn = value;
+ LOG_DEBUG("[ApplicationSettingsNew::setOperatorsOn] to %d", operatorsOn);
settings->setValue(settings::operators_on, std::to_string(value));
}
@@ 290,6 319,54 @@ namespace app
void ApplicationSettingsNew::setLockPassHash(unsigned int value)
{
lockPassHash = value;
- settings->setValue(::settings::SystemProperties::lockPassHash, std::to_string(value));
+ settings->setValue(
+ ::settings::SystemProperties::lockPassHash, std::to_string(value), ::settings::SettingsScope::Global);
+ }
+
+ auto ApplicationSettingsNew::getCurrentValues() -> settingsInterface::ScreenLightSettings::Values
+ {
+ constexpr int timeout = pdMS_TO_TICKS(1500);
+
+ auto response = sys::Bus::SendUnicast(
+ std::make_shared<sevm::ScreenLightControlRequestParameters>(), service::name::evt_manager, this, timeout);
+
+ if (response.first == sys::ReturnCodes::Success) {
+ auto msgState = dynamic_cast<sevm::ScreenLightControlParametersResponse *>(response.second.get());
+ if (msgState == nullptr) {
+ return {};
+ }
+
+ return {msgState->lightOn, msgState->mode, msgState->parameters};
+ }
+
+ return {};
+ }
+
+ void ApplicationSettingsNew::setBrightness(bsp::eink_frontlight::BrightnessPercentage value)
+ {
+ screen_light_control::Parameters parameters{value};
+ sys::Bus::SendUnicast(std::make_shared<sevm::ScreenLightControlMessage>(
+ screen_light_control::Action::setManualModeBrightness, parameters),
+ service::name::evt_manager,
+ this);
}
+
+ void ApplicationSettingsNew::setMode(bool isAutoLightSwitchOn)
+ {
+ sys::Bus::SendUnicast(std::make_shared<sevm::ScreenLightControlMessage>(
+ isAutoLightSwitchOn ? screen_light_control::Action::enableAutomaticMode
+ : screen_light_control::Action::disableAutomaticMode),
+ service::name::evt_manager,
+ this);
+ }
+
+ void ApplicationSettingsNew::setStatus(bool isDisplayLightSwitchOn)
+ {
+ sys::Bus::SendUnicast(
+ std::make_shared<sevm::ScreenLightControlMessage>(
+ isDisplayLightSwitchOn ? screen_light_control::Action::turnOn : screen_light_control::Action::turnOff),
+ service::name::evt_manager,
+ this);
+ }
+
} /* namespace app */
M module-apps/application-settings-new/ApplicationSettings.hpp => module-apps/application-settings-new/ApplicationSettings.hpp +43 -5
@@ 6,6 6,7 @@
#include "Application.hpp"
#include <bsp/common.hpp>
+#include <module-services/service-evtmgr/screen-light-control/ScreenLightControl.hpp>
namespace gui::window::name
{
@@ 16,6 17,7 @@ namespace gui::window::name
inline constexpr auto network = "Network";
inline constexpr auto apn_settings = "APNSettings";
+ inline constexpr auto apn_options = "APNOptions";
inline constexpr auto phone_modes = "PhoneModes";
inline constexpr auto apps_and_tools = "AppsAndTools";
inline constexpr auto security = "Security";
@@ 32,10 34,14 @@ namespace gui::window::name
inline constexpr auto nightshift = "Nightshift";
inline constexpr auto templates = "Templates";
- inline constexpr auto autolock = "Autolock";
- inline constexpr auto wallpaper = "Wallpaper";
- inline constexpr auto quotes = "Quotes";
- inline constexpr auto new_quote = "NewQuote";
+ inline constexpr auto autolock = "Autolock";
+ inline constexpr auto wallpaper = "Wallpaper";
+ inline constexpr auto quotes = "Quotes";
+ inline constexpr auto new_quote = "NewQuote";
+ inline constexpr auto edit_quote = "EditQuote";
+ inline constexpr auto options_quote = "OptionsQuote";
+ inline constexpr auto delete_quote = "DeleteQuote";
+ inline constexpr auto quotes_dialog_yes_no = "DialogYesNo";
inline constexpr auto display_and_keypad = "DisplayAndKeypad";
inline constexpr auto change_settings = "ChangeSettings";
@@ 44,6 50,14 @@ namespace gui::window::name
inline constexpr auto dialog_settings = "DialogSettings";
inline constexpr auto change_passcode = "ChangePasscode";
+ inline constexpr auto language = "Language";
+ inline constexpr auto date_and_time = "DateAndTime";
+ inline constexpr auto factory_reset = "FactoryReset";
+ inline constexpr auto about_your_pure = "AboutYourPure";
+ inline constexpr auto certification = "Certification";
+
+ inline constexpr auto new_apn = "NewApn";
+
} // namespace gui::window::name
namespace app
@@ 69,11 83,28 @@ namespace app
virtual void setVoLTEOn(bool value) = 0;
[[nodiscard]] virtual bool getVoLTEOn() const noexcept = 0;
};
+ class ScreenLightSettings
+ {
+ public:
+ struct Values
+ {
+ bool lightOn;
+ screen_light_control::ScreenLightMode mode;
+ screen_light_control::Parameters parameters;
+ };
+
+ virtual ~ScreenLightSettings() = default;
+ virtual auto getCurrentValues() -> Values = 0;
+ virtual void setBrightness(float brigtnessValue) = 0;
+ virtual void setMode(bool isAutoLightSwitchOn) = 0;
+ virtual void setStatus(bool isDisplayLightSwitchOn) = 0;
+ };
}; // namespace settingsInterface
class ApplicationSettingsNew : public app::Application,
public settingsInterface::SimParams,
- public settingsInterface::OperatorsSettings
+ public settingsInterface::OperatorsSettings,
+ public settingsInterface::ScreenLightSettings
{
public:
ApplicationSettingsNew(std::string name = name_settings_new,
@@ 106,7 137,14 @@ namespace app
}
void setLockPassHash(unsigned int value);
+ ScreenLightSettings::Values getCurrentValues() override;
+ void setBrightness(float brigtnessValue) override;
+ void setMode(bool isAutoLightSwitchOn) override;
+ void setStatus(bool isDisplayLightSwitchOn) override;
+
private:
+ void attachQuotesWindows();
+
Store::GSM::SIM selectedSim = Store::GSM::get()->selected;
std::string selectedSimNumber = {};
bsp::Board board = bsp::Board::none;
M module-apps/application-settings-new/CMakeLists.txt => module-apps/application-settings-new/CMakeLists.txt +13 -2
@@ 15,12 15,17 @@ target_sources( ${PROJECT_NAME}
PRIVATE
ApplicationSettings.cpp
+ models/ApnSettingsModel.cpp
+ models/NewApnModel.cpp
widgets/timeWidget.cpp
widgets/ChangePasscodeLockHandler.cpp
+ widgets/QuoteWidget.cpp
+ widgets/ApnInputWidget.cpp
windows/SettingsMainWindow.cpp
windows/AddDeviceWindow.cpp
windows/AllDevicesWindow.cpp
- windows/APNSettingsWindow.cpp
+ windows/ApnSettingsWindow.cpp
+ windows/ApnOptionsWindow.cpp
windows/BaseSettingsWindow.cpp
windows/BluetoothWindow.cpp
windows/FontSizeWindow.cpp
@@ 41,10 46,16 @@ target_sources( ${PROJECT_NAME}
windows/QuotesAddWindow.cpp
windows/SecurityMainWindow.cpp
windows/ChangePasscodeWindow.cpp
+ windows/NewApnWindow.cpp
+ widgets/SpinBox.cpp
+ widgets/SpinBoxOptionSetting.cpp
+ windows/SystemMainWindow.cpp
PUBLIC
ApplicationSettings.hpp
widgets/ChangePasscodeLockHandler.hpp
+ widgets/ApnInputWidget.hpp
+ windows/NewApnWindow.hpp
windows/SettingsMainWindow.hpp
windows/BaseSettingsWindow.hpp
windows/FontSizeWindow.hpp
@@ 59,6 70,7 @@ target_sources( ${PROJECT_NAME}
windows/AutolockWindow.hpp
windows/WallpaperWindow.hpp
windows/ChangePasscodeWindow.hpp
+ windows/SystemMainWindow.hpp
)
add_dependencies(${PROJECT_NAME} version)
@@ 66,5 78,4 @@ add_dependencies(${PROJECT_NAME} version)
target_link_libraries(${PROJECT_NAME}
PUBLIC
service-bluetooth
- service-evtmgr
)
A module-apps/application-settings-new/data/ApnListData.hpp => module-apps/application-settings-new/data/ApnListData.hpp +27 -0
@@ 0,0 1,27 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include <service-cellular/PacketDataTypes.hpp>
+#include <SwitchData.hpp>
+
+#include <vector>
+
+namespace gui
+{
+
+ class ApnListData : public SwitchData
+ {
+ public:
+ explicit ApnListData(std::vector<std::shared_ptr<packet_data::APN::Config>> apns) : apns(std::move(apns))
+ {}
+ [[nodiscard]] auto getAPNs() const noexcept -> const std::vector<std::shared_ptr<packet_data::APN::Config>> &
+ {
+ return apns;
+ }
+
+ private:
+ std::vector<std::shared_ptr<packet_data::APN::Config>> apns;
+ };
+} // namespace gui
A module-apps/application-settings-new/data/QuoteSwitchData.hpp => module-apps/application-settings-new/data/QuoteSwitchData.hpp +45 -0
@@ 0,0 1,45 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/models/QuotesModel.hpp"
+
+#include <SwitchData.hpp>
+#include <json/json11.hpp>
+#include <utility>
+
+namespace app
+{
+ class QuotesModel;
+};
+
+namespace gui
+{
+ enum class QuoteAction
+ {
+ None,
+ Add,
+ Edit
+ };
+
+ class QuoteSwitchData : public gui::SwitchData
+ {
+ public:
+ QuoteSwitchData(QuoteAction action, app::QuoteRecord quote = {}) : action(action), quote(std::move(quote))
+ {}
+
+ [[nodiscard]] auto getQuote() const
+ {
+ return quote;
+ }
+ [[nodiscard]] auto getAction() const
+ {
+ return action;
+ }
+
+ private:
+ QuoteAction action;
+ app::QuoteRecord quote;
+ };
+} // namespace gui
A module-apps/application-settings-new/data/SettingsInternals.hpp => module-apps/application-settings-new/data/SettingsInternals.hpp +30 -0
@@ 0,0 1,30 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include <cstdint>
+
+namespace settingsInternals
+{
+ enum class ListItemName
+ {
+ Name,
+ APN,
+ Proxy,
+ Port,
+ Username,
+ Password,
+
+ Server,
+ MMSC,
+ MmsProxy,
+ MmsPort,
+ MCC,
+ MNC,
+ AuthType,
+ ApnType,
+ ApnProtocol
+ };
+
+} // namespace settingsInternals
A module-apps/application-settings-new/data/SettingsItemData.hpp => module-apps/application-settings-new/data/SettingsItemData.hpp +23 -0
@@ 0,0 1,23 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include <service-cellular/service-cellular/PacketDataTypes.hpp>
+#include <ListItem.hpp>
+#include <SwitchData.hpp>
+
+class ApnItemData : public gui::SwitchData
+{
+ public:
+ ApnItemData(std::shared_ptr<packet_data::APN::Config> Apn) : apn(std::move(Apn)){};
+ ApnItemData() : apn(nullptr){};
+
+ auto getApn() -> std::shared_ptr<packet_data::APN::Config>
+ {
+ return apn;
+ }
+
+ private:
+ std::shared_ptr<packet_data::APN::Config> apn;
+};
A module-apps/application-settings-new/models/ApnSettingsModel.cpp => module-apps/application-settings-new/models/ApnSettingsModel.cpp +28 -0
@@ 0,0 1,28 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "ApnSettingsModel.hpp"
+#include <service-cellular/PacketDataCellularMessage.hpp>
+#include <service-cellular/ServiceCellular.hpp>
+
+ApnSettingsModel::ApnSettingsModel(app::Application *application) : application{application}
+{}
+
+void ApnSettingsModel::requestAPNList()
+{
+ sys::Bus::SendUnicast(std::make_shared<CellularGetAPNMessage>(), ServiceCellular::serviceName, application);
+}
+
+void ApnSettingsModel::saveAPN(std::shared_ptr<packet_data::APN::Config> apn)
+{
+ sys::Bus::SendUnicast(std::make_shared<CellularSetAPNMessage>(apn), ServiceCellular::serviceName, application);
+}
+
+void ApnSettingsModel::removeAPN(std::shared_ptr<packet_data::APN::Config> apn)
+{}
+
+void ApnSettingsModel::setAsDefaultAPN(std::shared_ptr<packet_data::APN::Config> apn)
+{
+ apn->apnType = packet_data::APN::APNType::Default;
+ sys::Bus::SendUnicast(std::make_shared<CellularSetAPNMessage>(apn), ServiceCellular::serviceName, application);
+}
A module-apps/application-settings-new/models/ApnSettingsModel.hpp => module-apps/application-settings-new/models/ApnSettingsModel.hpp +21 -0
@@ 0,0 1,21 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include <service-cellular/PacketDataTypes.hpp>
+#include <module-apps/Application.hpp>
+
+class ApnSettingsModel
+{
+ public:
+ ApnSettingsModel(app::Application *application);
+
+ void requestAPNList();
+ void saveAPN(std::shared_ptr<packet_data::APN::Config> apn);
+ void removeAPN(std::shared_ptr<packet_data::APN::Config> apn);
+ void setAsDefaultAPN(std::shared_ptr<packet_data::APN::Config> apn);
+
+ private:
+ app::Application *application = nullptr;
+};
A module-apps/application-settings-new/models/NewApnModel.cpp => module-apps/application-settings-new/models/NewApnModel.cpp +133 -0
@@ 0,0 1,133 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "NewApnModel.hpp"
+
+#include "application-settings-new/widgets/ApnInputWidget.hpp"
+
+#include <ListView.hpp>
+#include <time/ScopedTime.hpp>
+#include <BottomBar.hpp>
+
+NewApnModel::NewApnModel(app::Application *app) : application(app)
+{}
+
+auto NewApnModel::requestRecordsCount() -> unsigned int
+{
+ return internalData.size();
+}
+
+auto NewApnModel::getMinimalItemHeight() const -> unsigned int
+{
+ return style::settings::widget::apnInputWidget::h;
+}
+
+void NewApnModel::requestRecords(const uint32_t offset, const uint32_t limit)
+{
+ setupModel(offset, limit);
+ list->onProviderDataUpdate();
+}
+
+auto NewApnModel::getItem(gui::Order order) -> gui::ListItem *
+{
+ return getRecord(order);
+}
+
+void NewApnModel::createData()
+{
+ auto app = application;
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::Name,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::APN,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::Username,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::Password,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::AuthType,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::ApnType,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ internalData.emplace_back(new gui::ApnInputWidget(
+ settingsInternals::ListItemName::ApnProtocol,
+ [app](const UTF8 &text) { app->getCurrentWindow()->bottomBarTemporaryMode(text); },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); },
+ [app]() { app->getCurrentWindow()->selectSpecialCharacter(); },
+ [this]() { this->apnDataChanged(); }));
+
+ for (auto item : internalData) {
+ item->deleteByList = false;
+ }
+}
+
+void NewApnModel::clearData()
+{
+ list->clear();
+
+ eraseInternalData();
+
+ createData();
+
+ list->rebuildList();
+}
+
+void NewApnModel::saveData(std::shared_ptr<packet_data::APN::Config> apnRecord)
+{
+ for (auto item : internalData) {
+ if (item->onSaveCallback) {
+ item->onSaveCallback(apnRecord);
+ }
+ }
+}
+
+void NewApnModel::loadData(std::shared_ptr<packet_data::APN::Config> apnRecord)
+{
+ for (auto item : internalData) {
+ if (item->onLoadCallback) {
+ item->onLoadCallback(apnRecord);
+ }
+ }
+}
+
+void NewApnModel::apnDataChanged()
+{
+ for (auto item : internalData) {
+ if (item->onEmptyCallback && !item->onEmptyCallback()) {
+ application->getCurrentWindow()->setBottomBarActive(gui::BottomBar::Side::CENTER, true); // SAVE button
+ return;
+ }
+ }
+ application->getCurrentWindow()->setBottomBarActive(gui::BottomBar::Side::CENTER, false); // SAVE button
+ return;
+}
A module-apps/application-settings-new/models/NewApnModel.hpp => module-apps/application-settings-new/models/NewApnModel.hpp +35 -0
@@ 0,0 1,35 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/data/SettingsItemData.hpp"
+#include "application-settings-new/widgets/ApnListItem.hpp"
+#include "application-settings-new/widgets/SettingsStyle.hpp"
+#include "InternalModel.hpp"
+#include "Application.hpp"
+
+#include <ListItemProvider.hpp>
+
+class NewApnModel : public app::InternalModel<gui::ApnListItem *>, public gui::ListItemProvider
+{
+ app::Application *application = nullptr;
+
+ public:
+ NewApnModel(app::Application *app);
+
+ void clearData();
+ void saveData(std::shared_ptr<packet_data::APN::Config> apnRecord);
+ void loadData(std::shared_ptr<packet_data::APN::Config> apnRecord);
+
+ void createData();
+
+ [[nodiscard]] auto requestRecordsCount() -> unsigned int override;
+
+ [[nodiscard]] auto getMinimalItemHeight() const -> unsigned int override;
+
+ auto getItem(gui::Order order) -> gui::ListItem * override;
+
+ void requestRecords(const uint32_t offset, const uint32_t limit) override;
+ void apnDataChanged();
+};
A module-apps/application-settings-new/models/QuotesModel.cpp => module-apps/application-settings-new/models/QuotesModel.cpp +99 -0
@@ 0,0 1,99 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "application-settings-new/windows/QuotesMainWindow.hpp"
+#include "application-settings-new/ApplicationSettings.hpp"
+#include "QuotesRepository.hpp"
+#include "QuotesModel.hpp"
+
+#include <InputEvent.hpp>
+#include <i18n/i18n.hpp>
+#include <json/json11.hpp>
+#include <Utils.hpp>
+#include <string>
+#include <utility>
+
+namespace style::quotes::list
+{
+ constexpr auto item_height = 63;
+ constexpr auto max_quotes = 100;
+} // namespace style::quotes::list
+
+namespace app
+{
+ QuotesModel::QuotesModel(app::Application *app, std::unique_ptr<QuotesRepository> repository)
+ : application(app), repository(std::move(repository))
+ {}
+
+ auto QuotesModel::requestRecordsCount() -> unsigned int
+ {
+ return internalData.size();
+ }
+
+ auto QuotesModel::getMinimalItemHeight() const -> unsigned int
+ {
+ return style::quotes::list::item_height;
+ }
+
+ void QuotesModel::requestRecords(const uint32_t offset, const uint32_t limit)
+ {
+ setupModel(offset, limit);
+ list->onProviderDataUpdate();
+ }
+
+ auto QuotesModel::getItem(gui::Order order) -> gui::ListItem *
+ {
+ auto app = application;
+ auto *item = dynamic_cast<gui::QuoteWidget *>(getRecord(order));
+
+ if (item != nullptr) {
+ item->inputCallback = [app, item](gui::Item &, const gui::InputEvent &event) {
+ if (event.isShortPress() && event.is(gui::KeyCode::KEY_LF)) {
+ app->switchWindow(
+ gui::window::name::options_quote,
+ std::make_unique<gui::QuoteSwitchData>(gui::QuoteAction::None, item->getQuoteData()));
+ }
+ return false;
+ };
+ }
+ return item;
+ }
+
+ void QuotesModel::rebuild()
+ {
+ list->clear();
+ eraseInternalData();
+ createData();
+ list->rebuildList();
+ }
+
+ void QuotesModel::createData()
+ {
+ repository->get(0, style::quotes::list::max_quotes, [this](const std::list<QuoteRecord> "es, unsigned int) {
+ auto app = application;
+ for (const auto "e : quotes) {
+ auto item = new gui::QuoteWidget(
+ quote,
+ [app](const UTF8 &text) {
+ app->getCurrentWindow()->bottomBarTemporaryMode(text, gui::BottomBar::Side::CENTER, false);
+ },
+ [app]() { app->getCurrentWindow()->bottomBarRestoreFromTemporaryMode(); });
+
+ item->deleteByList = false;
+ internalData.push_back(item);
+ }
+ return true;
+ });
+ }
+
+ void QuotesModel::remove(const app::QuoteRecord "e)
+ {
+ repository->remove(quote);
+ }
+
+ void QuotesModel::save(const app::QuoteRecord "e)
+ {
+ repository->save(quote);
+ }
+
+} // namespace app
A module-apps/application-settings-new/models/QuotesModel.hpp => module-apps/application-settings-new/models/QuotesModel.hpp +42 -0
@@ 0,0 1,42 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "QuotesRepository.hpp"
+
+#include <purefs/filesystem_paths.hpp>
+#include <module-gui/gui/widgets/ListView.hpp>
+#include <module-apps/InternalModel.hpp>
+
+namespace gui
+{
+ class QuoteWidget;
+}
+
+namespace app
+{
+ class QuotesModel : public app::InternalModel<gui::QuoteWidget *>, public gui::ListItemProvider
+ {
+ public:
+ QuotesModel(app::Application *app, std::unique_ptr<QuotesRepository> repository);
+
+ [[nodiscard]] auto requestRecordsCount() -> unsigned int final;
+ [[nodiscard]] auto getMinimalItemHeight() const -> unsigned int final;
+
+ auto getItem(gui::Order order) -> gui::ListItem * final;
+ void requestRecords(const uint32_t offset, const uint32_t limit) final;
+
+ void rebuild();
+
+ void remove(const app::QuoteRecord "e);
+ void save(const app::QuoteRecord "e);
+
+ private:
+ void createData();
+
+ app::Application *application = nullptr;
+ std::unique_ptr<app::QuotesRepository> repository = nullptr;
+ };
+
+} // namespace app
A module-apps/application-settings-new/models/QuotesRepository.cpp => module-apps/application-settings-new/models/QuotesRepository.cpp +100 -0
@@ 0,0 1,100 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "QuotesRepository.hpp"
+
+#include <module-utils/gsl/gsl_util>
+#include <algorithm>
+#include <utility>
+
+namespace app
+{
+ QuotesJsonRepository::QuotesJsonRepository(const std::string &path) : repositoryPath{std::move(path)}
+ {}
+
+ void QuotesJsonRepository::get(std::uint32_t offset, std::uint32_t limit, const OnGetCallback &callback)
+ {
+ if (quotes.empty()) {
+ readQuotes(repositoryPath);
+ }
+
+ if (callback) {
+ std::uint32_t size = quotes.size();
+ auto start = std::next(quotes.begin(), std::min(offset, size));
+ auto end = std::next(quotes.begin(), std::min(offset + limit, size));
+ std::list<QuoteRecord> result{start, end};
+ callback(result, result.size());
+ }
+ }
+
+ void QuotesJsonRepository::save(const QuoteRecord "e)
+ {
+ auto toEdit = std::find_if(quotes.begin(), quotes.end(), [quote](auto &&d) { return d.id == quote.id; });
+
+ if (toEdit != quotes.end()) {
+ toEdit->quote = quote.quote;
+ toEdit->author = quote.author;
+ }
+ else if (quote.id == 0) {
+ quotes.push_back(quote);
+ }
+
+ writeQuotes(repositoryPath);
+ }
+
+ void QuotesJsonRepository::remove(const QuoteRecord "e)
+ {
+ quotes.remove_if([quote](auto &&d) { return d.id == quote.id; });
+ writeQuotes(repositoryPath);
+ }
+
+ void QuotesJsonRepository::writeQuotes(const fs::path "esFilename)
+ {
+ if (auto file = std::fopen(repositoryPath.c_str(), "w"); file != nullptr) {
+ auto _ = gsl::finally([file] { std::fclose(file); });
+ auto body = json11::Json{quotes};
+ auto text = body.dump();
+ std::fwrite(text.c_str(), 1, text.length(), file);
+ }
+ }
+
+ void QuotesJsonRepository::readQuotes(const fs::path "esFilename)
+ {
+ std::string err;
+
+ const auto fileContents = readFileToString(quotesFilename);
+ auto obj = json11::Json::parse(fileContents.c_str(), err).array_items();
+
+ if (!err.empty()) {
+ LOG_ERROR("Error while parsing quotes from file: %s error: %s ", quotesFilename.c_str(), err.c_str());
+ return;
+ }
+
+ quotes.clear();
+
+ auto id = 1;
+ std::transform(obj.begin(), obj.end(), std::back_inserter(quotes), [&id](auto item) {
+ return QuoteRecord{id++, item["quote"].string_value(), item["author"].string_value()};
+ });
+ }
+
+ auto QuotesJsonRepository::readFileToString(const fs::path &filename) -> std::string
+ {
+ constexpr auto tar_buf = 8192 * 4;
+ auto file = std::fopen(filename.c_str(), "r");
+ if (file == nullptr) {
+ return {};
+ }
+ auto _ = gsl::finally([file] { std::fclose(file); });
+ const auto length = utils::filesystem::filelength(file);
+
+ if (length >= tar_buf) {
+ LOG_ERROR("File %s length is too high!", filename.c_str());
+ return {};
+ }
+ LOG_INFO("file length: %ld", length);
+ auto buffer = std::make_unique<char[]>(length + 1);
+ std::fread(buffer.get(), 1, length, file);
+ return std::string(buffer.get());
+ }
+} // namespace app
A module-apps/application-settings-new/models/QuotesRepository.hpp => module-apps/application-settings-new/models/QuotesRepository.hpp +58 -0
@@ 0,0 1,58 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include <json/json11.hpp>
+
+#include <list>
+#include <functional>
+#include <module-apps/Application.hpp>
+
+namespace app
+{
+ struct QuoteRecord
+ {
+ int id = 0;
+ std::string quote;
+ std::string author;
+
+ [[nodiscard]] auto to_json() const -> json11::Json
+ {
+ return json11::Json::object{{"quote", quote}, {"author", author}};
+ }
+ };
+
+ class QuotesRepository
+ {
+ public:
+ using OnGetCallback = std::function<bool(const std::list<QuoteRecord> &, unsigned int)>;
+
+ virtual ~QuotesRepository() noexcept = default;
+
+ virtual void get(std::uint32_t offset, std::uint32_t limit, const OnGetCallback &callback) = 0;
+ virtual void save(const QuoteRecord "e) = 0;
+ virtual void remove(const QuoteRecord "e) = 0;
+ };
+
+ class QuotesJsonRepository : public QuotesRepository
+ {
+ public:
+ QuotesJsonRepository(const std::string &path);
+
+ void get(std::uint32_t offset, std::uint32_t limit, const OnGetCallback &callback) override;
+ void save(const QuoteRecord "e) override;
+ void remove(const QuoteRecord "e) override;
+
+ private:
+ void writeQuotes(const fs::path &path);
+ void readQuotes(const fs::path &fn);
+ std::string readFileToString(const fs::path &fn);
+
+ std::list<QuoteRecord> quotes;
+ std::string repositoryPath;
+ };
+} // namespace app
A module-apps/application-settings-new/widgets/ApnInputWidget.cpp => module-apps/application-settings-new/widgets/ApnInputWidget.cpp +221 -0
@@ 0,0 1,221 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "ApnInputWidget.hpp"
+#include <Span.hpp>
+#include "application-settings-new/widgets/SettingsStyle.hpp"
+#include <i18n/i18n.hpp>
+#include <utility>
+
+namespace gui
+{
+ ApnInputWidget::ApnInputWidget(settingsInternals::ListItemName listItemName,
+ std::function<void(const UTF8 &)> bottomBarTemporaryMode,
+ std::function<void()> bottomBarRestoreFromTemporaryMode,
+ std::function<void()> selectSpecialCharacter,
+ std::function<void()> contentChanged,
+ unsigned int lines)
+ : listItemName(listItemName), checkTextContent(std::move(contentChanged))
+ {
+
+ setMinimumSize(style::settings::widget::apnInputWidget::w,
+ style::settings::widget::apnInputWidget::title_label_h +
+ style::settings::widget::apnInputWidget::span_size +
+ style::settings::widget::apnInputWidget::input_text_h * lines);
+
+ setMargins(gui::Margins(0, style::margins::huge, 0, 0));
+
+ vBox = new VBox(this, 0, 0, 0, 0);
+ vBox->setEdges(RectangleEdge::None);
+
+ titleLabel = new Label(vBox);
+ titleLabel->setMinimumSize(style::settings::widget::apnInputWidget::w,
+ style::settings::widget::apnInputWidget::title_label_h);
+ titleLabel->setEdges(RectangleEdge::None);
+ titleLabel->setAlignment(Alignment(gui::Alignment::Horizontal::Left, gui::Alignment::Vertical::Top));
+ titleLabel->setFont(style::window::font::verysmall);
+ titleLabel->activeItem = false;
+
+ inputText = new TextFixedSize(vBox, 0, 0, 0, 0);
+ inputText->setMinimumSize(style::settings::widget::apnInputWidget::w,
+ style::settings::widget::apnInputWidget::input_text_h * lines);
+ inputText->setMargins(Margins(0, style::settings::widget::apnInputWidget::span_size, 0, 0));
+ inputText->setUnderlinePadding(style::settings::widget::apnInputWidget::underline_padding);
+
+ inputText->setEdges(RectangleEdge::None);
+ inputText->setAlignment(Alignment(gui::Alignment::Horizontal::Left, gui::Alignment::Vertical::Top));
+ inputText->setFont(style::window::font::medium);
+ inputText->setInputMode(new InputMode(
+ {InputMode::ABC, InputMode::abc, InputMode::digit},
+ [=](const UTF8 &text) { bottomBarTemporaryMode(text); },
+ [=]() { bottomBarRestoreFromTemporaryMode(); },
+ [=]() { selectSpecialCharacter(); }));
+ inputText->setPenFocusWidth(style::window::default_border_focus_w);
+ inputText->setPenWidth(style::window::default_border_no_focus_w);
+ inputText->setEditMode(EditMode::Edit);
+
+ applyItemNameSpecificSettings();
+
+ focusChangedCallback = [&](Item &item) {
+ setFocusItem(focus ? vBox : nullptr);
+
+ auto tempText = inputText->getText();
+
+ if (focus) {
+ inputText->setFont(style::window::font::mediumbold);
+ inputText->setText(tempText);
+ }
+ else {
+ inputText->setFont(style::window::font::medium);
+ inputText->setText(tempText);
+ }
+ return true;
+ };
+
+ inputCallback = [&](Item &item, const InputEvent &event) {
+ auto result = inputText->onInput(event);
+ if (checkTextContent != nullptr) {
+ checkTextContent();
+ }
+ return result;
+ };
+ setEdges(RectangleEdge::None);
+ }
+
+ auto ApnInputWidget::onDimensionChanged(const BoundingBox &oldDim, const BoundingBox &newDim) -> bool
+ {
+ vBox->setPosition(0, 0);
+ vBox->setSize(newDim.w, newDim.h);
+
+ return true;
+ }
+
+ void ApnInputWidget::applyItemNameSpecificSettings()
+ {
+ switch (listItemName) {
+
+ case settingsInternals::ListItemName::Name:
+ nameHandler();
+ break;
+
+ case settingsInternals::ListItemName::APN:
+ apnHandler();
+ break;
+
+ case settingsInternals::ListItemName::Username:
+ usernameHandler();
+ break;
+
+ case settingsInternals::ListItemName::Password:
+ passwordNumberHandler();
+ break;
+
+ case settingsInternals::ListItemName::AuthType:
+ authtypeHandler();
+ break;
+
+ case settingsInternals::ListItemName::ApnType:
+ apntypeHandler();
+ break;
+
+ case settingsInternals::ListItemName::ApnProtocol:
+ protocolHandler();
+ break;
+
+ default:
+ LOG_ERROR("Incorrect List Item Name!");
+ break;
+ }
+ }
+
+ void ApnInputWidget::nameHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_name"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->apn = inputText->getText();
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->apn);
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+
+ void ApnInputWidget::apnHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_APN"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->ip = inputText->getText();
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->ip);
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+
+ void ApnInputWidget::usernameHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_username"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->username = inputText->getText();
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->username);
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+
+ void ApnInputWidget::passwordNumberHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_password"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->password = inputText->getText();
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->password);
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+
+ void ApnInputWidget::authtypeHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_authtype"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->setAuthMethod(inputText->getText());
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->getAuthMethod());
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+
+ void ApnInputWidget::apntypeHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_apntype"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->setApnType(inputText->getText());
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->getApnType());
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+ void ApnInputWidget::protocolHandler()
+ {
+ titleLabel->setText(utils::localize.get("app_settings_apn_apnprotocol"));
+ inputText->setTextType(TextType::SingleLine);
+ onSaveCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ apnRecord->setApnProtocol(inputText->getText());
+ };
+ onLoadCallback = [&](std::shared_ptr<packet_data::APN::Config> apnRecord) {
+ inputText->setText(apnRecord->getApnProtocol());
+ };
+ onEmptyCallback = [&]() { return inputText->isEmpty(); };
+ }
+
+} /* namespace gui */
A module-apps/application-settings-new/widgets/ApnInputWidget.hpp => module-apps/application-settings-new/widgets/ApnInputWidget.hpp +44 -0
@@ 0,0 1,44 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/data/SettingsInternals.hpp"
+#include "application-settings-new//widgets/ApnListItem.hpp"
+
+#include <ListItem.hpp>
+#include <Text.hpp>
+#include <TextFixedSize.hpp>
+
+namespace gui
+{
+ class ApnInputWidget : public ApnListItem
+ {
+ settingsInternals::ListItemName listItemName;
+
+ public:
+ ApnInputWidget(settingsInternals::ListItemName listItemName,
+ std::function<void(const UTF8 &text)> bottomBarTemporaryMode = nullptr,
+ std::function<void()> bottomBarRestoreFromTemporaryMode = nullptr,
+ std::function<void()> selectSpecialCharacter = nullptr,
+ std::function<void()> contentChanged = nullptr,
+ unsigned int lines = 1);
+
+ private:
+ VBox *vBox = nullptr;
+ Label *titleLabel = nullptr;
+ TextFixedSize *inputText = nullptr;
+ std::function<void()> checkTextContent = nullptr;
+
+ void applyItemNameSpecificSettings();
+ auto onDimensionChanged(const BoundingBox &oldDim, const BoundingBox &newDim) -> bool override;
+ void nameHandler();
+ void apnHandler();
+ void usernameHandler();
+ void passwordNumberHandler();
+ void authtypeHandler();
+ void apntypeHandler();
+ void protocolHandler();
+ };
+
+} /* namespace gui */
A module-apps/application-settings-new/widgets/ApnListItem.hpp => module-apps/application-settings-new/widgets/ApnListItem.hpp +18 -0
@@ 0,0 1,18 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/data/SettingsItemData.hpp"
+
+namespace gui
+{
+ class ApnListItem : public ListItem
+ {
+ public:
+ std::function<void(std::shared_ptr<packet_data::APN::Config> apnRecord)> onSaveCallback = nullptr;
+ std::function<void(std::shared_ptr<packet_data::APN::Config> apnRecord)> onLoadCallback = nullptr;
+ std::function<bool()> onEmptyCallback = nullptr;
+ };
+
+} /* namespace gui */
A module-apps/application-settings-new/widgets/OptionSetting.hpp => module-apps/application-settings-new/widgets/OptionSetting.hpp +30 -0
@@ 0,0 1,30 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "SpinBox.hpp"
+#include "OptionWindow.hpp"
+#include "Application.hpp"
+
+#include <module-apps/options/type/OptionSetting.hpp>
+
+namespace gui
+{
+ class SpinBoxOptionSettings : public option::OptionSettings
+ {
+ public:
+ SpinBoxOptionSettings(UTF8 text,
+ uint8_t value,
+ uint8_t maxValue,
+ std::function<bool(uint8_t)> updateCallback,
+ std::function<bool(Item &)> focusChangedCallback = nullptr);
+
+ [[nodiscard]] auto build() const -> ListItem * override;
+
+ private:
+ std::function<bool(uint8_t)> updateCallback;
+ std::uint8_t maxValue;
+ std::uint8_t value;
+ };
+} // namespace gui
A module-apps/application-settings-new/widgets/QuoteWidget.cpp => module-apps/application-settings-new/widgets/QuoteWidget.cpp +117 -0
@@ 0,0 1,117 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "QuoteWidget.hpp"
+
+#include <BottomBar.hpp>
+#include <InputEvent.hpp>
+#include <utility>
+#include <i18n/i18n.hpp>
+
+namespace style::quotes
+{
+ namespace widget
+ {
+ inline constexpr uint32_t w = style::window::default_body_width;
+ inline constexpr uint32_t h = 50;
+
+ inline constexpr uint32_t input_box_w = 55;
+ inline constexpr uint32_t input_box_h = h;
+ inline constexpr int32_t input_box_right_margin = 20;
+
+ inline constexpr uint32_t description_label_w = 280;
+ inline constexpr uint32_t description_label_h = 33;
+ inline constexpr int32_t description_label_right_margin = 40;
+
+ inline constexpr int32_t tick_image_left_margin = -64;
+ inline constexpr int32_t tick_image_right_margin = 32;
+
+ } // namespace widget
+
+} // namespace style::quotes
+
+namespace gui
+{
+
+ QuoteWidget::QuoteWidget(const app::QuoteRecord "e,
+ std::function<void(const UTF8 &)> bottomBarTemporaryMode,
+ std::function<void()> bottomBarRestoreFromTemporaryMode)
+ : bottomBarTemporaryMode(std::move(bottomBarTemporaryMode)),
+ bottomBarRestoreFromTemporaryMode(std::move(bottomBarRestoreFromTemporaryMode)), quote(quote)
+ {
+
+ setMinimumSize(style::quotes::widget::w, style::quotes::widget::h);
+
+ setMargins(gui::Margins(0, style::margins::big, 0, 0));
+
+ hBox = new gui::HBox(this, 0, 0, this->getWidth(), 80);
+ hBox->setEdges(gui::RectangleEdge::None);
+ hBox->setPenFocusWidth(style::window::default_border_focus_w);
+ hBox->setPenWidth(style::window::default_border_rect_no_focus);
+
+ inputBoxLabel = new gui::Label(hBox, 0, 0, 0, 0);
+ inputBoxLabel->setMinimumSize(style::quotes::widget::input_box_w, style::quotes::widget::input_box_h);
+
+ inputBoxLabel->setMargins(gui::Margins(0, 0, style::quotes::widget::input_box_right_margin, 0));
+ inputBoxLabel->setEdges(gui::RectangleEdge::Bottom);
+ inputBoxLabel->setAlignment(Alignment(gui::Alignment::Horizontal::Center, gui::Alignment::Vertical::Center));
+ inputBoxLabel->setFont(style::window::font::medium);
+ inputBoxLabel->activeItem = false;
+
+ tickImage = new gui::Image(hBox, 0, 0, 0, 0);
+ tickImage->setAlignment(Alignment(gui::Alignment::Vertical::Center));
+ // Not ideal -> best solution would be to create separate widget with image inside box.
+ tickImage->setMargins(gui::Margins(
+ style::quotes::widget::tick_image_left_margin, 0, style::quotes::widget::tick_image_right_margin, 0));
+ tickImage->set("small_tick_W_M");
+ tickImage->setVisible(true);
+ tickImage->activeItem = false;
+
+ descriptionLabel = new gui::Label(hBox, 0, 0, 0, 0);
+ descriptionLabel->setMinimumSize(style::quotes::widget::description_label_w,
+ style::quotes::widget::description_label_h);
+ descriptionLabel->setMargins(gui::Margins(0, 0, style::quotes::widget::description_label_right_margin, 0));
+ descriptionLabel->setEdges(gui::RectangleEdge::None);
+ descriptionLabel->setAlignment(Alignment(gui::Alignment::Horizontal::Left, gui::Alignment::Vertical::Center));
+ descriptionLabel->setFont(style::window::font::medium);
+ descriptionLabel->activeItem = false;
+
+ descriptionLabel->setText(quote.quote);
+
+ focusChangedCallback = [&](gui::Item &item) {
+ if (item.focus) {
+ descriptionLabel->setFont(style::footer::font::bold);
+ setFocusItem(inputBoxLabel);
+ auto bottorBarText =
+ tickImage->visible ? utils::localize.get("common_uncheck") : utils::localize.get("common_check");
+ this->bottomBarTemporaryMode(bottorBarText);
+ }
+ else {
+ descriptionLabel->setFont(style::footer::font::medium);
+ setFocusItem(nullptr);
+ this->bottomBarRestoreFromTemporaryMode();
+ }
+ return true;
+ };
+
+ activatedCallback = [&](gui::Item &item) {
+ tickImage->setVisible(!tickImage->visible);
+ auto bottorBarText =
+ tickImage->visible ? utils::localize.get("common_uncheck") : utils::localize.get("common_check");
+ this->bottomBarTemporaryMode(bottorBarText);
+ hBox->resizeItems();
+ return true;
+ };
+
+ setEdges(gui::RectangleEdge::None);
+ }
+
+ auto QuoteWidget::onDimensionChanged(const BoundingBox &oldDim, const BoundingBox &newDim) -> bool
+ {
+ hBox->setPosition(0, 0);
+ hBox->setSize(newDim.w, newDim.h);
+
+ return true;
+ }
+
+} /* namespace gui */
A module-apps/application-settings-new/widgets/QuoteWidget.hpp => module-apps/application-settings-new/widgets/QuoteWidget.hpp +42 -0
@@ 0,0 1,42 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/data/QuoteSwitchData.hpp"
+
+#include <BoxLayout.hpp>
+#include <Image.hpp>
+#include <Label.hpp>
+#include <ListItem.hpp>
+#include <json/json11.hpp>
+
+namespace gui
+{
+ class QuoteWidget : public ListItem
+ {
+ public:
+ QuoteWidget(const app::QuoteRecord "e,
+ std::function<void(const UTF8 &text)> bottomBarTemporaryMode = nullptr,
+ std::function<void()> bottomBarRestoreFromTemporaryMode = nullptr);
+
+ auto onDimensionChanged(const BoundingBox &oldDim, const BoundingBox &newDim) -> bool override;
+
+ [[nodiscard]] auto getQuoteData() const -> app::QuoteRecord
+ {
+ return quote;
+ }
+
+ private:
+ gui::HBox *hBox = nullptr;
+ gui::Label *inputBoxLabel = nullptr;
+ gui::Label *descriptionLabel = nullptr;
+ gui::Image *tickImage = nullptr;
+
+ std::function<void(const UTF8 &text)> bottomBarTemporaryMode = nullptr;
+ std::function<void()> bottomBarRestoreFromTemporaryMode = nullptr;
+
+ app::QuoteRecord quote;
+ };
+
+} /* namespace gui */
M module-apps/application-settings-new/widgets/SettingsStyle.hpp => module-apps/application-settings-new/widgets/SettingsStyle.hpp +20 -0
@@ 28,7 28,18 @@ namespace style
inline constexpr auto before_noon = "AM";
inline constexpr auto after_noon = "PM";
} // namespace time
+
+ namespace apnInputWidget
+ {
+ inline constexpr uint32_t w = style::window::default_body_width;
+ inline constexpr uint32_t h = 63;
+ inline constexpr uint32_t title_label_h = 20;
+ inline constexpr uint32_t input_text_h = 37;
+ inline constexpr uint32_t span_size = 6;
+ inline constexpr int32_t underline_padding = 4;
+ } // namespace apnInputWidget
} // namespace widget
+
namespace window
{
namespace leftArrowImage
@@ 70,6 81,15 @@ namespace style
inline constexpr auto separator_h = 55;
} // namespace nightshift
+
+ namespace newApn
+ {
+ inline constexpr uint32_t x = style::window::default_left_margin;
+ inline constexpr uint32_t y = style::header::height;
+ inline constexpr uint32_t w = style::listview::body_width_with_scroll;
+ inline constexpr uint32_t h = style::window_height - y - style::footer::height;
+ } // namespace newApn
+
} // namespace window
}; // namespace settings
} // namespace style
A module-apps/application-settings-new/widgets/SpinBox.cpp => module-apps/application-settings-new/widgets/SpinBox.cpp +93 -0
@@ 0,0 1,93 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "SpinBox.hpp"
+#include "widgets/BarGraph.hpp"
+
+#include <InputEvent.hpp>
+#include <Label.hpp>
+#include <Image.hpp>
+#include <utf8/UTF8.hpp>
+#include <utility>
+
+namespace gui
+{
+ SpinBox::SpinBox(
+ Item *parent, const std::string &title, UpdateCallback updateCallback, uint8_t maxValue, uint8_t startValue)
+ : HBox(parent, style::window::default_left_margin), updateBarCallback(std::move(updateCallback))
+ {
+ setMinimumSize(style::window::default_body_width, style::window::label::big_h);
+ setPenWidth(style::window::default_border_no_focus_w);
+ setPenFocusWidth(style::window::default_border_focus_w);
+ setEdges(gui::RectangleEdge::Top | gui::RectangleEdge::Bottom);
+
+ titleLabel = addTitle(this, title);
+ leftArrow = addArrow(this, "arrow_left", Alignment::Horizontal::Left, false);
+ rightArrow = addArrow(this, "arrow_right", Alignment::Horizontal::Right, false);
+ bar = addBarGraph(this, maxValue, startValue);
+
+ focusChangedCallback = [this](Item &item) {
+ leftArrow->setVisible(item.focus);
+ rightArrow->setVisible(item.focus);
+ resizeItems();
+ return true;
+ };
+
+ inputCallback = [this](gui::Item &item, const gui::InputEvent &event) {
+ if (!event.isShortPress()) {
+ return false;
+ }
+
+ int update = 0;
+ if (event.is(KeyCode::KEY_LEFT)) {
+ update = -1;
+ }
+ else if (event.is(KeyCode::KEY_RIGHT)) {
+ update = 1;
+ }
+
+ if (update != 0 && bar->update(update)) {
+ updateBarCallback(bar->getValue());
+ return true;
+ }
+
+ return false;
+ };
+ }
+
+ Image *SpinBox::addArrow(Item *parent, const std::string &arrowName, Alignment::Horizontal aligment, bool visible)
+ {
+ auto arrow = new Image(parent, 0, 0, 0, 0);
+ arrow->setAlignment(Alignment(aligment, Alignment::Vertical::Center));
+ arrow->setMargins(Margins(0, 0, style::margins::big, 0));
+ arrow->set(arrowName);
+ arrow->setVisible(visible);
+
+ return arrow;
+ }
+
+ Label *SpinBox::addTitle(Item *parent, const std::string &text)
+ {
+ auto label = new Label(parent);
+ label->setMinimumHeight(style::window::label::default_h);
+ label->setMaximumWidth(style::window::default_body_width);
+
+ label->setEdges(RectangleEdge::None);
+ label->setAlignment(Alignment(gui::Alignment::Horizontal::Left, gui::Alignment::Vertical::Center));
+ label->setFont(style::window::font::big);
+ label->setText(text);
+ label->activeItem = false;
+
+ return label;
+ }
+
+ HBarGraph *SpinBox::addBarGraph(Item *parent, uint8_t maxValue, uint8_t startValue)
+ {
+ auto barGraph = new HBarGraph(parent, 0, 0, maxValue);
+ barGraph->setAlignment(Alignment(gui::Alignment::Horizontal::Right, gui::Alignment::Vertical::Center));
+ barGraph->setValue(startValue);
+ barGraph->activeItem = false;
+
+ return barGraph;
+ }
+} // namespace gui
A module-apps/application-settings-new/widgets/SpinBox.hpp => module-apps/application-settings-new/widgets/SpinBox.hpp +43 -0
@@ 0,0 1,43 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+#include "widgets/BarGraph.hpp"
+
+namespace style::settings::brightness
+{
+ inline constexpr auto max_value = 6;
+};
+
+class UTF8;
+
+namespace gui
+{
+ class Image;
+ class SpinBox : public HBox
+ {
+ public:
+ using UpdateCallback = std::function<bool(uint8_t)>;
+
+ SpinBox(Item *parent,
+ const std::string &title,
+ UpdateCallback updateCallback,
+ std::uint8_t maxValue = style::settings::brightness::max_value,
+ std::uint8_t startValue = 0);
+
+ private:
+ auto addArrow(Item *parent, const std::string &arrowName, Alignment::Horizontal aligment, bool visible)
+ -> Image *;
+ auto addBarGraph(Item *parent, uint8_t maxValue, uint8_t startValue) -> HBarGraph *;
+ auto addTitle(Item *parent, const std::string &text) -> Label *;
+
+ HBarGraph *bar;
+ Label *titleLabel;
+ Image *leftArrow;
+ Image *rightArrow;
+ UpdateCallback updateBarCallback;
+ };
+} // namespace gui
A module-apps/application-settings-new/widgets/SpinBoxOptionSetting.cpp => module-apps/application-settings-new/widgets/SpinBoxOptionSetting.cpp +41 -0
@@ 0,0 1,41 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "OptionSetting.hpp"
+
+#include <utility>
+#include "SpinBox.hpp"
+
+namespace gui
+{
+ SpinBoxOptionSettings::SpinBoxOptionSettings(UTF8 text,
+ std::uint8_t value,
+ std::uint8_t maxValue,
+ std::function<bool(uint8_t)> updateCallback,
+ std::function<bool(Item &)> focusChangedCallback)
+ : option::OptionSettings(text, nullptr, focusChangedCallback, nullptr),
+ updateCallback(std::move(updateCallback)), maxValue(maxValue), value(value)
+ {}
+
+ auto SpinBoxOptionSettings::build() const -> ListItem *
+ {
+ auto spinBox = new SpinBox(nullptr, text, updateCallback, maxValue, value);
+
+ auto optionItem = new gui::ListItem();
+ optionItem->setMinimumSize(style::window::default_body_width, style::window::label::big_h);
+ optionItem->inputCallback = spinBox->inputCallback;
+ optionItem->focusChangedCallback = [spinBox, this](Item &item) {
+ spinBox->focusChangedCallback(item);
+ return focusChangedCallback(item);
+ };
+ optionItem->dimensionChangedCallback = [spinBox](gui::Item &, const BoundingBox &newDim) -> bool {
+ spinBox->setPosition(0, 0);
+ spinBox->setSize(newDim.w, newDim.h);
+ return true;
+ };
+
+ optionItem->addWidget(spinBox);
+
+ return optionItem;
+ }
+} // namespace gui
D module-apps/application-settings-new/windows/APNSettingsWindow.cpp => module-apps/application-settings-new/windows/APNSettingsWindow.cpp +0 -61
@@ 1,61 0,0 @@
-// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
-// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-
-#include "APNSettingsWindow.hpp"
-#include "application-settings-new/ApplicationSettings.hpp"
-#include "application-settings-new/widgets/SettingsStyle.hpp"
-#include "OptionSetting.hpp"
-
-#include <InputEvent.hpp>
-
-namespace gui
-{
-
- APNSettingsWindow::APNSettingsWindow(app::Application *app) : OptionWindow(app, gui::window::name::apn_settings)
- {
- buildInterface();
- }
-
- auto APNSettingsWindow::onInput(const InputEvent &inputEvent) -> bool
- {
-
- if (inputEvent.isShortPress()) {
- if (inputEvent.is(KeyCode::KEY_LEFT)) {
- // switch to new/edit APN window
- }
- }
-
- return AppWindow::onInput(inputEvent);
- }
- void APNSettingsWindow::buildInterface()
- {
- setTitle(utils::localize.get("app_settings_network_apn_settings"));
-
- topBar->setActive(TopBar::Elements::SIGNAL, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
-
- leftArrowImage = new gui::Image(this,
- style::settings::window::leftArrowImage::x,
- style::settings::window::leftArrowImage::y,
- style::settings::window::leftArrowImage::w,
- style::settings::window::leftArrowImage::h,
- "arrow_left");
- crossImage = new gui::Image(this,
- style::settings::window::crossImage::x,
- style::settings::window::crossImage::y,
- style::settings::window::crossImage::w,
- style::settings::window::crossImage::h,
- "cross");
- emptyListIcon = new Icon(this,
- 0,
- style::header::height,
- style::window_width,
- style::window_height - style::header::height - style::footer::height,
- "phonebook_empty_grey_circle_W_G",
- utils::localize.get("app_settings_network_apn_settings_no_apns"));
-
- bottomBar->setActive(gui::BottomBar::Side::CENTER, false);
- }
-
-} // namespace gui
M module-apps/application-settings-new/windows/AllDevicesWindow.cpp => module-apps/application-settings-new/windows/AllDevicesWindow.cpp +0 -4
@@ 71,10 71,6 @@ namespace gui
gui::option::SettingRightItem::Bt));
}
- topBar->setActive(TopBar::Elements::SIGNAL, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
-
leftArrowImage = new gui::Image(this,
style::settings::window::leftArrowImage::x,
style::settings::window::leftArrowImage::y,
A module-apps/application-settings-new/windows/ApnOptionsWindow.cpp => module-apps/application-settings-new/windows/ApnOptionsWindow.cpp +73 -0
@@ 0,0 1,73 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "ApnOptionsWindow.hpp"
+
+#include "application-settings-new/ApplicationSettings.hpp"
+#include "application-settings-new/data/SettingsItemData.hpp"
+#include "application-settings-new/models/ApnSettingsModel.hpp"
+#include "OptionSetting.hpp"
+
+namespace gui
+{
+ ApnOptionsWindow::ApnOptionsWindow(app::Application *app) : BaseSettingsWindow(app, window::name::apn_options)
+ {
+ setTitle(utils::localize.get("app_settings_apn_options"));
+ apnSettingsModel = new ApnSettingsModel(application);
+ }
+
+ auto ApnOptionsWindow::buildOptionsList() -> std::list<gui::Option>
+ {
+ std::list<gui::Option> optionsList;
+
+ optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
+ utils::localize.get("app_settings_apn_options_edit"),
+ [=](gui::Item &item) {
+ std::unique_ptr<gui::SwitchData> data = std::make_unique<ApnItemData>(apn);
+ application->switchWindow(gui::window::name::new_apn, gui::ShowMode::GUI_SHOW_INIT, std::move(data));
+ return true;
+ },
+ nullptr,
+ this));
+
+ optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
+ utils::localize.get("app_settings_apn_options_delete"),
+ [=](gui::Item &item) {
+ apnSettingsModel->removeAPN(apn);
+ return true;
+ },
+ nullptr,
+ this));
+
+ optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
+ utils::localize.get("app_settings_apn_options_set_as_default"),
+ [=](gui::Item &item) {
+ apnSettingsModel->setAsDefaultAPN(apn);
+ return true;
+ },
+ nullptr,
+ this));
+
+ return optionsList;
+ }
+
+ auto ApnOptionsWindow::handleSwitchData(SwitchData *data) -> bool
+ {
+ if (data == nullptr) {
+ return false;
+ }
+
+ auto item = dynamic_cast<ApnItemData *>(data);
+ if (item == nullptr) {
+ return false;
+ }
+
+ apn = item->getApn();
+ if (apn == nullptr) {
+ apn = std::make_shared<packet_data::APN::Config>();
+ return true;
+ }
+
+ return true;
+ }
+} // namespace gui
A module-apps/application-settings-new/windows/ApnOptionsWindow.hpp => module-apps/application-settings-new/windows/ApnOptionsWindow.hpp +25 -0
@@ 0,0 1,25 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/models/ApnSettingsModel.hpp"
+#include "BaseSettingsWindow.hpp"
+
+#include <service-cellular/PacketDataTypes.hpp>
+
+namespace gui
+{
+
+ class ApnOptionsWindow : public BaseSettingsWindow
+ {
+ public:
+ ApnOptionsWindow(app::Application *app);
+
+ private:
+ auto buildOptionsList() -> std::list<gui::Option> override;
+ auto handleSwitchData(SwitchData *data) -> bool override;
+ std::shared_ptr<packet_data::APN::Config> apn;
+ ApnSettingsModel *apnSettingsModel = nullptr;
+ };
+} // namespace gui
A module-apps/application-settings-new/windows/ApnSettingsWindow.cpp => module-apps/application-settings-new/windows/ApnSettingsWindow.cpp +135 -0
@@ 0,0 1,135 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "ApnSettingsWindow.hpp"
+#include "application-settings-new/ApplicationSettings.hpp"
+#include "application-settings-new/data/ApnListData.hpp"
+#include "application-settings-new/models/ApnSettingsModel.hpp"
+#include "application-settings-new/widgets/SettingsStyle.hpp"
+#include "application-settings-new/data/SettingsItemData.hpp"
+#include "OptionSetting.hpp"
+
+#include <InputEvent.hpp>
+
+namespace gui
+{
+
+ ApnSettingsWindow::ApnSettingsWindow(app::Application *app) : OptionWindow(app, gui::window::name::apn_settings)
+ {
+ buildInterface();
+ }
+
+ void ApnSettingsWindow::buildInterface()
+ {
+ setTitle(utils::localize.get("app_settings_network_apn_settings"));
+
+ leftArrowImage = new gui::Image(this,
+ style::settings::window::leftArrowImage::x,
+ style::settings::window::leftArrowImage::y,
+ style::settings::window::leftArrowImage::w,
+ style::settings::window::leftArrowImage::h,
+ "arrow_left");
+ crossImage = new gui::Image(this,
+ style::settings::window::crossImage::x,
+ style::settings::window::crossImage::y,
+ style::settings::window::crossImage::w,
+ style::settings::window::crossImage::h,
+ "cross");
+ emptyListIcon = new Icon(this,
+ 0,
+ style::header::height,
+ style::window_width,
+ style::window_height - style::header::height - style::footer::height,
+ "phonebook_empty_grey_circle_W_G",
+ utils::localize.get("app_settings_apn_settings_no_apns"));
+
+ bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get(style::strings::common::options));
+
+ auto apnSettingsModel = new ApnSettingsModel(application);
+ apnSettingsModel->requestAPNList();
+ }
+ auto ApnSettingsWindow::handleSwitchData(SwitchData *data) -> bool
+ {
+ if (data == nullptr) {
+ LOG_ERROR("Received nullptr");
+ return false;
+ }
+
+ const auto newData = dynamic_cast<ApnListData *>(data);
+ if (newData == nullptr) {
+ LOG_ERROR("Received nullptr");
+ return false;
+ }
+
+ apns = newData->getAPNs();
+ if (apns.empty()) {
+ emptyListIcon->setVisible(true);
+ return false;
+ }
+
+ return true;
+ }
+
+ void ApnSettingsWindow::onBeforeShow(ShowMode mode, SwitchData *data)
+ {
+ clearOptions();
+ bottomBar->setActive(gui::BottomBar::Side::LEFT, false);
+ bottomBar->setActive(gui::BottomBar::Side::CENTER, false);
+ emptyListIcon->setVisible(false);
+
+ if (apns.empty()) {
+ return;
+ }
+
+ addOptions(optionsList(apns));
+ bottomBar->setActive(gui::BottomBar::Side::LEFT, true);
+ bottomBar->setActive(gui::BottomBar::Side::CENTER, true);
+ }
+
+ auto ApnSettingsWindow::onInput(const InputEvent &inputEvent) -> bool
+ {
+ if (AppWindow::onInput(inputEvent)) {
+ return true;
+ }
+ if (!inputEvent.isShortPress()) {
+ return false;
+ }
+ if (inputEvent.is(gui::KeyCode::KEY_LEFT)) {
+ auto apnRecord = std::make_shared<packet_data::APN::Config>();
+ std::unique_ptr<gui::SwitchData> data = std::make_unique<ApnItemData>(apnRecord);
+ application->switchWindow(gui::window::name::new_apn, gui::ShowMode::GUI_SHOW_INIT, std::move(data));
+ return true;
+ }
+ if (inputEvent.is(gui::KeyCode::KEY_LF)) {
+ auto apnRecord = std::make_shared<packet_data::APN::Config>();
+ std::unique_ptr<gui::SwitchData> data = std::make_unique<ApnItemData>(apnRecord);
+ application->switchWindow(gui::window::name::apn_options, gui::ShowMode::GUI_SHOW_INIT, std::move(data));
+ return true;
+ }
+
+ return false;
+ }
+
+ auto ApnSettingsWindow::optionsList(std::vector<std::shared_ptr<packet_data::APN::Config>> apnsList)
+ -> std::list<Option>
+ {
+ std::list<gui::Option> optionsList;
+
+ for (const auto &apn : apnsList) {
+ optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
+ (apn->apnType == packet_data::APN::APNType::Default) ? "<b>" + apn->apn + "</b>" : apn->apn,
+ [=](gui::Item &item) {
+ LOG_DEBUG("APN: %s", apn->apn.c_str());
+ std::unique_ptr<gui::SwitchData> apnData = std::make_unique<ApnItemData>(apn);
+ application->switchWindow(
+ gui::window::name::new_apn, gui::ShowMode::GUI_SHOW_INIT, std::move(apnData));
+ return true;
+ },
+ nullptr,
+ nullptr));
+ }
+
+ return optionsList;
+ }
+
+} // namespace gui
R module-apps/application-settings-new/windows/APNSettingsWindow.hpp => module-apps/application-settings-new/windows/ApnSettingsWindow.hpp +7 -2
@@ 5,20 5,25 @@
#include "OptionWindow.hpp"
#include <Icon.hpp>
+#include <service-cellular/PacketDataTypes.hpp>
namespace gui
{
- class APNSettingsWindow : public OptionWindow
+ class ApnSettingsWindow : public OptionWindow
{
public:
- APNSettingsWindow(app::Application *app);
+ ApnSettingsWindow(app::Application *app);
private:
void buildInterface() override;
+ auto handleSwitchData(SwitchData *data) -> bool override;
+ void onBeforeShow(ShowMode mode, SwitchData *data) override;
auto onInput(const InputEvent &inputEvent) -> bool override;
+ auto optionsList(std::vector<std::shared_ptr<packet_data::APN::Config>> vector) -> std::list<Option>;
Image *leftArrowImage = nullptr;
Image *crossImage = nullptr;
Icon *emptyListIcon = nullptr;
+ std::vector<std::shared_ptr<packet_data::APN::Config>> apns;
};
}; // namespace gui
M module-apps/application-settings-new/windows/AppsAndToolsWindow.cpp => module-apps/application-settings-new/windows/AppsAndToolsWindow.cpp +0 -4
@@ 33,10 33,6 @@ namespace gui
gui::option::Arrow::Enabled});
};
- topBar->setActive(TopBar::Elements::SIGNAL, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
-
addMenu(i18("app_settings_apps_messages"), gui::window::name::messages);
addMenu(i18("app_settings_apps_torch"), gui::window::name::torch);
M module-apps/application-settings-new/windows/BaseSettingsWindow.cpp => module-apps/application-settings-new/windows/BaseSettingsWindow.cpp +0 -4
@@ 2,7 2,6 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "BaseSettingsWindow.hpp"
-
#include <i18n/i18n.hpp>
namespace gui
@@ 17,9 16,6 @@ namespace gui
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
- topBar->setActive(TopBar::Elements::TIME, true);
}
void BaseSettingsWindow::destroyInterface()
M module-apps/application-settings-new/windows/BaseSettingsWindow.hpp => module-apps/application-settings-new/windows/BaseSettingsWindow.hpp +1 -0
@@ 6,6 6,7 @@
#include "Application.hpp"
#include "windows/AppWindow.hpp"
#include "windows/OptionWindow.hpp"
+#include <service-db/Settings.hpp>
namespace gui
{
M module-apps/application-settings-new/windows/BluetoothWindow.cpp => module-apps/application-settings-new/windows/BluetoothWindow.cpp +0 -2
@@ 15,8 15,6 @@ namespace gui
BluetoothWindow::BluetoothWindow(app::Application *app) : OptionWindow(app, gui::window::name::bluetooth)
{
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
sys::Bus::SendUnicast(
std::make_shared<::message::bluetooth::RequestStatus>(), service::name::bluetooth, application);
}
M module-apps/application-settings-new/windows/ChangePasscodeWindow.cpp => module-apps/application-settings-new/windows/ChangePasscodeWindow.cpp +0 -8
@@ 76,14 76,6 @@ namespace gui
setTitle(utils::localize.get("app_settings_security_change_passcode"));
}
- void ChangePasscodeWindow::buildTopBar()
- {
- topBar->setActive(TopBar::Elements::SIM, false);
- topBar->setActive(TopBar::Elements::LOCK, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::TIME, true);
- }
-
void ChangePasscodeWindow::destroyInterface()
{
erase();
M module-apps/application-settings-new/windows/ChangePasscodeWindow.hpp => module-apps/application-settings-new/windows/ChangePasscodeWindow.hpp +0 -1
@@ 21,7 21,6 @@ namespace gui
void buildBottomBar() override;
void buildInterface() override;
void buildTitleBar() override;
- void buildTopBar() override;
void destroyInterface() override;
void onBeforeShow(ShowMode mode, SwitchData *data) override;
void processPasscode();
M module-apps/application-settings-new/windows/DisplayLightWindow.cpp => module-apps/application-settings-new/windows/DisplayLightWindow.cpp +50 -14
@@ 2,23 2,37 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "DisplayLightWindow.hpp"
-
+#include "application-settings-new/widgets/OptionSetting.hpp"
+#include "OptionSetting.hpp"
#include "application-settings-new/ApplicationSettings.hpp"
#include "OptionSetting.hpp"
+#include <service-evtmgr/screen-light-control/ScreenLightControl.hpp>
#include <i18n/i18n.hpp>
+#include <Service/Bus.hpp>
namespace gui
{
- DisplayLightWindow::DisplayLightWindow(app::Application *app) : BaseSettingsWindow(app, window::name::display_light)
+ DisplayLightWindow::DisplayLightWindow(app::Application *app, app::settingsInterface::ScreenLightSettings *settings)
+ : BaseSettingsWindow(app, window::name::display_light), screenLightSettings(settings)
{
+ auto values = screenLightSettings->getCurrentValues();
+
+ isDisplayLightSwitchOn = values.lightOn;
+ isAutoLightSwitchOn = values.mode == screen_light_control::ScreenLightMode::Automatic;
+ brightnessValue = values.parameters.manualModeBrightness;
+
setTitle(utils::localize.get("app_settings_display_display_light"));
}
void DisplayLightWindow::switchHandler(bool &onOffSwitch)
{
onOffSwitch = !onOffSwitch;
+
rebuildOptionList();
+
+ screenLightSettings->setStatus(isDisplayLightSwitchOn);
+ screenLightSettings->setMode(isAutoLightSwitchOn);
}
auto DisplayLightWindow::buildOptionsList() -> std::list<gui::Option>
@@ 49,21 63,43 @@ namespace gui
}
if (isDisplayLightSwitchOn && !isAutoLightSwitchOn) {
- optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
- utils::translateI18("app_settings_display_light_brightness"),
- [=](gui::Item &item) { return true; },
- [=](gui::Item &item) {
- if (item.focus) {
- this->setBottomBarText(utils::translateI18(style::strings::common::set),
- BottomBar::Side::CENTER);
- }
- return true;
- },
- this,
- gui::option::SettingRightItem::ArrowWhite));
+ addBrightnessOption(optionsList);
}
return optionsList;
}
+ auto DisplayLightWindow::createBrightnessOption(int brightnessStep) -> std::unique_ptr<SpinBoxOptionSettings>
+ {
+ auto setBrightness = [this, brightnessStep](uint8_t value) {
+ screenLightSettings->setBrightness(value * brightnessStep);
+ return true;
+ };
+
+ auto setBottomBarOnSpinnerFocus = [&](gui::Item &item) {
+ if (item.focus) {
+ setBottomBarText(utils::translateI18(style::strings::common::set), BottomBar::Side::CENTER);
+ }
+ return true;
+ };
+
+ auto spinner = std::make_unique<gui::SpinBoxOptionSettings>(
+ utils::translateI18("app_settings_display_light_brightness") + " " + utils::to_string(brightnessStep),
+ brightnessValue * brightnessStep,
+ std::ceil(screen_light_control::Parameters::MAX_BRIGHTNESS / brightnessStep),
+ setBrightness,
+ setBottomBarOnSpinnerFocus);
+
+ return spinner;
+ }
+
+ void DisplayLightWindow::addBrightnessOption(std::list<gui::Option> &options)
+ {
+ /*
+ * We are adding 4 brightness widgets to easily check what is the best step for setting screen brightness.
+ */
+ for (auto step : {10, 15, 20, 25}) {
+ options.emplace_back(createBrightnessOption(step));
+ }
+ }
} // namespace gui
M module-apps/application-settings-new/windows/DisplayLightWindow.hpp => module-apps/application-settings-new/windows/DisplayLightWindow.hpp +13 -5
@@ 3,21 3,29 @@
#pragma once
+#include <module-services/service-evtmgr/screen-light-control/ScreenLightControl.hpp>
+#include <module-apps/application-settings-new/widgets/SpinBox.hpp>
+#include <module-apps/application-settings-new/ApplicationSettings.hpp>
+#include <module-apps/application-settings-new/widgets/OptionSetting.hpp>
#include "BaseSettingsWindow.hpp"
namespace gui
{
-
class DisplayLightWindow : public BaseSettingsWindow
{
public:
- DisplayLightWindow(app::Application *app);
+ DisplayLightWindow(app::Application *app, app::settingsInterface::ScreenLightSettings *screenLightSettings);
private:
- void switchHandler(bool &onOffSwitch);
auto buildOptionsList() -> std::list<Option> override;
+ void switchHandler(bool &onOffSwitch);
+
+ void addBrightnessOption(std::list<Option> &);
+ auto createBrightnessOption(int step) -> std::unique_ptr<SpinBoxOptionSettings>;
- bool isDisplayLightSwitchOn = false;
- bool isAutoLightSwitchOn = false;
+ bool isDisplayLightSwitchOn = false;
+ bool isAutoLightSwitchOn = false;
+ std::uint8_t brightnessValue = 0;
+ app::settingsInterface::ScreenLightSettings *screenLightSettings = nullptr;
};
} // namespace gui
M module-apps/application-settings-new/windows/MessagesWindow.cpp => module-apps/application-settings-new/windows/MessagesWindow.cpp +0 -3
@@ 64,9 64,6 @@ namespace gui
};
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
- topBar->setActive(TopBar::Elements::SIGNAL, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
addMenuSwitch(utils::translateI18("app_settings_show_unread_first"), "");
addMenu(utils::translateI18("app_settings_Templates"), gui::window::name::templates);
M module-apps/application-settings-new/windows/NetworkWindow.cpp => module-apps/application-settings-new/windows/NetworkWindow.cpp +0 -3
@@ 122,9 122,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
- topBar->setActive(TopBar::Elements::SIGNAL, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
return optList;
}
void NetworkWindow::rebuild()
A module-apps/application-settings-new/windows/NewApnWindow.cpp => module-apps/application-settings-new/windows/NewApnWindow.cpp +119 -0
@@ 0,0 1,119 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "NewApnWindow.hpp"
+#include "application-settings-new/ApplicationSettings.hpp"
+
+#include <Dialog.hpp>
+#include <messages/DialogMetadataMessage.hpp>
+
+namespace gui
+{
+
+ NewApnWindow::NewApnWindow(app::Application *app)
+ : AppWindow(app, gui::window::name::new_apn), newApnModel{std::make_shared<NewApnModel>(app)}
+ {
+ buildInterface();
+ }
+
+ void NewApnWindow::rebuild()
+ {
+ destroyInterface();
+ buildInterface();
+ }
+
+ void NewApnWindow::buildInterface()
+ {
+ AppWindow::buildInterface();
+
+ bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::save));
+ bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
+
+ setTitle(utils::localize.get("app_settings_new_edit_apn"));
+
+ list = new gui::ListView(this,
+ style::settings::window::newApn::x,
+ style::settings::window::newApn::y,
+ style::settings::window::newApn::w,
+ style::settings::window::newApn::h,
+ newApnModel);
+ setFocusItem(list);
+ apnSettingsModel = new ApnSettingsModel(application);
+ }
+
+ void NewApnWindow::destroyInterface()
+ {
+ erase();
+ }
+
+ void NewApnWindow::onBeforeShow(ShowMode mode, SwitchData *data)
+ {
+ if (mode != ShowMode::GUI_SHOW_RETURN) {
+ newApnModel->clearData();
+ }
+
+ if (mode == ShowMode::GUI_SHOW_INIT) {
+ list->rebuildList();
+ }
+
+ if (apn != nullptr) {
+ newApnModel->loadData(apn);
+ }
+ }
+
+ auto NewApnWindow::handleSwitchData(SwitchData *data) -> bool
+ {
+ setSaveButtonVisible(false);
+
+ if (data == nullptr) {
+ return false;
+ }
+
+ auto *item = dynamic_cast<ApnItemData *>(data);
+ if (item == nullptr) {
+ return false;
+ }
+
+ apn = item->getApn();
+ if (apn == nullptr) {
+ apn = std::make_shared<packet_data::APN::Config>();
+ return true;
+ }
+
+ return true;
+ }
+
+ void NewApnWindow::setSaveButtonVisible(bool visible)
+ {
+ bottomBar->setActive(BottomBar::Side::CENTER, visible);
+ }
+
+ auto NewApnWindow::onInput(const InputEvent &inputEvent) -> bool
+ {
+ if (!inputEvent.isShortPress()) {
+ return false;
+ }
+ if (inputEvent.is(gui::KeyCode::KEY_ENTER)) {
+ if (apn != nullptr) {
+ newApnModel->saveData(apn);
+ }
+ verifyAndSave();
+ return true;
+ }
+
+ return AppWindow::onInput(inputEvent);
+ }
+
+ auto NewApnWindow::verifyAndSave() -> bool
+ {
+ if (apn == nullptr) {
+ LOG_DEBUG("APN record not found");
+ return false;
+ }
+ apnSettingsModel->saveAPN(apn);
+ LOG_DEBUG("APN record saved : \"%s\" ", apn->apn.c_str());
+
+ return true;
+ }
+
+} // namespace gui
A module-apps/application-settings-new/windows/NewApnWindow.hpp => module-apps/application-settings-new/windows/NewApnWindow.hpp +35 -0
@@ 0,0 1,35 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "application-settings-new/models/ApnSettingsModel.hpp"
+#include "application-settings-new/models/NewApnModel.hpp"
+
+#include <AppWindow.hpp>
+#include <ListView.hpp>
+#include <Text.hpp>
+
+namespace gui
+{
+ class NewApnWindow : public AppWindow
+ {
+ public:
+ NewApnWindow(app::Application *app);
+
+ private:
+ auto onInput(const InputEvent &inputEvent) -> bool override;
+ void onBeforeShow(ShowMode mode, SwitchData *data) override;
+ auto handleSwitchData(SwitchData *data) -> bool override;
+ void rebuild() override;
+ void buildInterface() override;
+ void destroyInterface() override;
+ auto verifyAndSave() -> bool;
+ void setSaveButtonVisible(bool visible);
+ std::shared_ptr<packet_data::APN::Config> apn;
+ std::shared_ptr<NewApnModel> newApnModel;
+ ApnSettingsModel *apnSettingsModel = nullptr;
+ gui::ListView *list = nullptr;
+ };
+
+} /* namespace gui */
M module-apps/application-settings-new/windows/NightshiftWindow.cpp => module-apps/application-settings-new/windows/NightshiftWindow.cpp +0 -3
@@ 16,9 16,6 @@ namespace gui
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::SIM, false);
- topBar->setActive(TopBar::Elements::TIME, true);
-
setTitle(utils::localize.get("app_settings_title_nightshift"));
body = new gui::VBox(this,
M module-apps/application-settings-new/windows/PhoneNameWindow.cpp => module-apps/application-settings-new/windows/PhoneNameWindow.cpp +0 -2
@@ 22,8 22,6 @@ namespace gui
void PhoneNameWindow::buildInterface()
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::SIM, false);
- topBar->setActive(TopBar::Elements::TIME, true);
setTitle(utils::localize.get("app_settings_bluetooth_phone_name"));
M module-apps/application-settings-new/windows/QuotesAddWindow.cpp => module-apps/application-settings-new/windows/QuotesAddWindow.cpp +165 -10
@@ 2,32 2,187 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "QuotesAddWindow.hpp"
+#include "QuotesMainWindow.hpp"
#include "application-settings-new/ApplicationSettings.hpp"
+#include "application-settings-new/data/QuoteSwitchData.hpp"
+#include "application-settings-new/models/QuotesRepository.hpp"
#include <i18n/i18n.hpp>
#include <widgets/Text.hpp>
+namespace style
+{
+ constexpr auto counterWidth = 70;
+ constexpr auto headerWidth = style::window::default_body_width - counterWidth;
+} // namespace style
+
namespace gui
{
- QuotesAddWindow::QuotesAddWindow(app::Application *app) : AppWindow(app, gui::window::name::quotes)
+ namespace
+ {
+ constexpr auto maxQuoteCharactersCount = 150U;
+ constexpr auto maxQuoteLinesCount = 4;
+ constexpr auto maxAuthorCharactersCount = 30U;
+
+ auto formatCounterText(uint32_t counter, uint32_t maxValue) -> std::string
+ {
+ std::ostringstream counterText;
+ counterText << counter << '/' << maxValue;
+ return counterText.str();
+ }
+ } // namespace
+
+ QuoteAddEditWindow::QuoteAddEditWindow(app::Application *app, std::shared_ptr<app::QuotesModel> model)
+ : AppWindow(app, gui::window::name::quotes), quoteModel(std::move(model))
{
- setTitle(utils::localize.get("app_settings_display_locked_screen_new_quote"));
+ buildInterface();
}
- void QuotesAddWindow::buildInterface()
+ void QuoteAddEditWindow::buildInterface()
{
+ AppWindow::buildInterface();
+
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::save));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- auto text = new gui::Text(nullptr,
- style::window::default_left_margin,
- title->offset_h() + style::margins::big,
- style::window::default_body_width,
- style::window::default_body_height);
+ auto vBox = new VBox(this,
+ style::window::default_left_margin,
+ style::header::height + style::margins::very_big,
+ style::window::default_body_width,
+ style::window::default_body_height);
+
+ vBox->setEdges(RectangleEdge::None);
+ vBox->setPenFocusWidth(::style::window::default_border_focus_w);
+ vBox->setPenWidth(::style::window::default_border_rect_no_focus);
+
+ auto quoteHeader = new HBox(vBox, 0, 0, 0, 0);
+ quoteHeader->setMinimumSize(style::window::default_body_width, style::window::label::default_h);
+ quoteHeader->activeItem = false;
+ quoteHeader->setEdges(gui::RectangleEdge::None);
+
+ auto quoteLabel = new Label(quoteHeader, 0, 0, 0, 0);
+ quoteLabel->setMinimumSize(style::headerWidth, style::window::label::default_h);
+ quoteLabel->setEdges(RectangleEdge::None);
+ quoteLabel->setPenFocusWidth(::style::window::default_border_focus_w);
+ quoteLabel->setText(utils::localize.get("app_settings_display_wallpaper_quotes_quote"));
+ quoteLabel->setFont(::style::window::font::verysmall);
+ quoteLabel->setAlignment(gui::Alignment{gui::Alignment::Horizontal::Left});
+ quoteLabel->activeItem = false;
+
+ quoteCharCounter = new gui::Label(quoteHeader, 0, 0, 0, 0);
+ quoteCharCounter->setMinimumSize(style::counterWidth, style::window::label::default_h);
+ quoteCharCounter->setEdges(gui::RectangleEdge::None);
+ quoteCharCounter->setFont(::style::window::font::verysmall);
+ quoteCharCounter->setAlignment(gui::Alignment{gui::Alignment::Horizontal::Right});
+
+ quoteText = new gui::Text(vBox, 0, 0, 0, 0);
+ quoteText->setAlignment(gui::Alignment{gui::Alignment::Vertical::Top});
+ quoteText->setMinimumSize(style::window::default_body_width,
+ style::window::label::default_h * maxQuoteLinesCount);
+ quoteText->setPenFocusWidth(::style::window::default_border_focus_w);
+ quoteText->setPenWidth(::style::window::default_border_rect_no_focus);
+ quoteText->setEdges(gui::RectangleEdge::None);
+ quoteText->setFont(::style::window::font::medium);
+ quoteText->setInputMode(new InputMode(
+ {InputMode::ABC, InputMode::abc, InputMode::digit},
+ [=](const UTF8 &text) { bottomBarTemporaryMode(text); },
+ [=]() { bottomBarRestoreFromTemporaryMode(); },
+ [=]() { selectSpecialCharacter(); }));
+ quoteText->setTextLimitType(gui::TextLimitType::MaxSignsCount, maxQuoteCharactersCount);
+ quoteText->setTextChangedCallback([this](Item &, const UTF8 &text) { setQuoteCharactersCount(text.length()); });
+
+ auto authorHeader = new HBox(vBox, 0, 0, 0, 0);
+ authorHeader->setMinimumSize(style::window::default_body_width, style::window::label::default_h);
+ authorHeader->setEdges(gui::RectangleEdge::None);
+ authorHeader->activeItem = false;
+
+ auto authorLabel = new Label(authorHeader, 0, 0, 0, 0);
+ authorLabel->setMinimumSize(style::headerWidth, style::window::label::default_h);
+ authorLabel->setEdges(RectangleEdge::None);
+ authorLabel->setAlignment(gui::Alignment{gui::Alignment::Horizontal::Left});
+ authorLabel->setText(utils::localize.get("app_settings_display_wallpaper_quotes_author"));
+ authorLabel->setPenFocusWidth(::style::window::default_border_focus_w);
+ authorLabel->setFont(::style::window::font::verysmall);
+ authorLabel->setPadding(gui::Padding(0, 0, 0, 0));
+ authorLabel->activeItem = false;
+
+ authorCharCounter = new gui::Label(authorHeader, 0, 0, 0, 0);
+ authorCharCounter->setMinimumSize(style::counterWidth, style::window::label::default_h);
+ authorCharCounter->setEdges(gui::RectangleEdge::None);
+ authorCharCounter->setFont(::style::window::font::verysmall);
+ authorCharCounter->setAlignment(gui::Alignment{gui::Alignment::Horizontal::Right});
+
+ authorText = new gui::Text(vBox, 0, 0, 0, 0);
+ authorText->setMinimumSize(style::window::default_body_width, style::window::label::default_h);
+ authorText->setAlignment(gui::Alignment{gui::Alignment::Vertical::Top});
+ authorText->setPenFocusWidth(::style::window::default_border_focus_w);
+ authorText->setPenWidth(::style::window::default_border_rect_no_focus);
+ authorText->setEdges(gui::RectangleEdge::None);
+ authorText->setFont(::style::window::font::medium);
+ authorText->setInputMode(new InputMode(
+ {InputMode::ABC, InputMode::abc, InputMode::digit},
+ [=](const UTF8 &text) { bottomBarTemporaryMode(text); },
+ [=]() { bottomBarRestoreFromTemporaryMode(); },
+ [=]() { selectSpecialCharacter(); }));
+ authorText->setTextLimitType(gui::TextLimitType::MaxSignsCount, maxAuthorCharactersCount);
+ authorText->setTextChangedCallback(
+ [this](Item &, const UTF8 &text) { setAuthorCharactersCount(text.length()); });
+
+ setTitle(utils::localize.get("app_settings_display_wallpaper_quotes_new"));
+ vBox->resizeItems();
+ setFocusItem(quoteText);
+ }
- addWidget(text);
- setFocusItem(text);
+ void QuoteAddEditWindow::onBeforeShow(ShowMode mode, SwitchData *data)
+ {
+ auto *quotedata = dynamic_cast<QuoteSwitchData *>(data);
+ if (quotedata == nullptr) {
+ return;
+ }
+
+ quoteAction = quotedata->getAction();
+ quoteData = quotedata->getQuote();
+
+ if (quoteAction == QuoteAction::Edit) {
+ setTitle(utils::localize.get("app_settings_display_wallpaper_quotes_edit"));
+ quoteText->setText(quoteData.quote);
+ authorText->setText(quoteData.author);
+ }
+ else {
+ setTitle(utils::localize.get("app_settings_display_wallpaper_quotes_new"));
+ }
+
+ setAuthorCharactersCount(authorText->getText().length());
+ setQuoteCharactersCount(quoteText->getText().length());
+ }
+
+ bool QuoteAddEditWindow::onInput(const gui::InputEvent &inputEvent)
+ {
+ if (inputEvent.isShortPress() && inputEvent.is(gui::KeyCode::KEY_ENTER)) {
+ LOG_DEBUG("Save Quote: %s", quoteText->getText().c_str());
+ quoteData.quote = quoteText->getText();
+ quoteData.author = authorText->getText();
+ quoteModel->save(quoteData);
+
+ auto backToOptionWindow = 1;
+ auto backToMainWindow = 2;
+
+ auto windowToBack = quoteAction == QuoteAction::Add ? backToOptionWindow : backToMainWindow;
+ application->returnToPreviousWindow(windowToBack);
+ }
+
+ return AppWindow::onInput(inputEvent);
+ }
+
+ void QuoteAddEditWindow::setAuthorCharactersCount(std::uint32_t count)
+ {
+ authorCharCounter->setText(formatCounterText(count, maxAuthorCharactersCount));
+ }
+
+ void QuoteAddEditWindow::setQuoteCharactersCount(std::uint32_t count)
+ {
+ quoteCharCounter->setText(formatCounterText(count, maxQuoteCharactersCount));
}
} // namespace gui
M module-apps/application-settings-new/windows/QuotesAddWindow.hpp => module-apps/application-settings-new/windows/QuotesAddWindow.hpp +17 -3
@@ 4,18 4,32 @@
#pragma once
#include "BaseSettingsWindow.hpp"
+#include "QuotesMainWindow.hpp"
+#include "application-settings-new/models/QuotesModel.hpp"
namespace gui
{
class CheckBoxWithLabel;
- class QuotesAddWindow : public AppWindow
+ class QuoteAddEditWindow : public AppWindow
{
public:
- QuotesAddWindow(app::Application *app);
+ QuoteAddEditWindow(app::Application *app, std::shared_ptr<app::QuotesModel> model);
void buildInterface() override;
private:
- std::vector<CheckBoxWithLabel *> boxes;
+ auto onInput(const InputEvent &inputEvent) -> bool override;
+ void onBeforeShow(ShowMode mode, SwitchData *data) override;
+ void setAuthorCharactersCount(uint32_t count);
+ void setQuoteCharactersCount(uint32_t count);
+
+ gui::Text *quoteText = nullptr;
+ gui::Text *authorText = nullptr;
+ gui::Label *authorCharCounter = nullptr;
+ gui::Label *quoteCharCounter = nullptr;
+
+ QuoteAction quoteAction;
+ app::QuoteRecord quoteData;
+ std::shared_ptr<app::QuotesModel> quoteModel;
};
} // namespace gui
M module-apps/application-settings-new/windows/QuotesMainWindow.cpp => module-apps/application-settings-new/windows/QuotesMainWindow.cpp +52 -74
@@ 2,7 2,8 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "QuotesMainWindow.hpp"
-
+#include "application-settings-new/models/QuotesRepository.hpp"
+#include "application-settings-new/models/QuotesModel.hpp"
#include "application-settings-new/ApplicationSettings.hpp"
#include "application-settings-new/widgets/SettingsStyle.hpp"
#include "OptionSetting.hpp"
@@ 10,17 11,54 @@
#include <InputEvent.hpp>
#include <i18n/i18n.hpp>
#include <json/json11.hpp>
-#include <purefs/filesystem_paths.hpp>
-#include <Utils.hpp>
-#include <string>
+#include <utility>
+
+namespace style::quotes
+{
+ namespace list
+ {
+ constexpr auto X = style::window::default_left_margin;
+ constexpr auto Y = style::header::height;
+ constexpr auto Width = style::listview::body_width_with_scroll;
+ constexpr auto Height = style::window_height - Y - style::footer::height;
+ } // namespace list
+
+ inline constexpr auto cross_x = 48;
+ inline constexpr auto cross_y = 55;
+ inline constexpr auto arrow_x = 30;
+ inline constexpr auto arrow_y = 62;
+
+} // namespace style::quotes
namespace gui
{
- QuotesMainWindow::QuotesMainWindow(app::Application *app) : BaseSettingsWindow(app, gui::window::name::quotes)
+ QuotesMainWindow::QuotesMainWindow(app::Application *app, std::shared_ptr<app::QuotesModel> model)
+ : AppWindow(app, gui::window::name::quotes), quotesModel(std::move(model))
{
- const auto quotesPath = purefs::dir::getCurrentOSPath() / "data/applications/settings/quotes.json";
- setTitle(utils::localize.get("app_settings_display_locked_screen_quotes"));
- readQuotes(quotesPath);
+ buildInterface();
+ }
+
+ void QuotesMainWindow::buildInterface()
+ {
+ AppWindow::buildInterface();
+
+ setTitle(utils::localize.get("app_settings_display_wallpaper_quotes"));
+
+ bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::check));
+ bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
+ bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get(style::strings::common::options));
+
+ new gui::Image(this, style::quotes::arrow_x, style::quotes::arrow_y, 0, 0, "arrow_left");
+ new gui::Image(this, style::quotes::cross_x, style::quotes::cross_y, 0, 0, "cross");
+
+ list = new gui::ListView(this,
+ style::quotes::list::X,
+ style::quotes::list::Y,
+ style::quotes::list::Width,
+ style::quotes::list::Height,
+ quotesModel);
+
+ setFocusItem(list);
}
auto QuotesMainWindow::onInput(const InputEvent &inputEvent) -> bool
@@ 29,10 67,12 @@ namespace gui
if (AppWindow::onInput(inputEvent)) {
return true;
}
- if (inputEvent.state == InputEvent::State::keyReleasedShort) {
+
+ if (inputEvent.isShortPress()) {
switch (inputEvent.keyCode) {
case gui::KeyCode::KEY_LEFT:
- application->switchWindow(gui::window::name::new_quote, nullptr);
+ application->switchWindow(gui::window::name::new_quote,
+ std::make_unique<QuoteSwitchData>(QuoteAction::Add));
return true;
default:
break;
@@ 41,70 81,8 @@ namespace gui
return false;
}
- void QuotesMainWindow::readQuotes(fs::path fn)
- {
- std::string err;
-
- const auto fileContents = readFileToString(fn);
- auto obj = json11::Json::parse(fileContents.c_str(), err).array_items();
-
- if (!err.empty()) {
- LOG_ERROR("Error while parsing quotes: %s", err.c_str());
- }
-
- std::transform(obj.begin(), obj.end(), std::back_inserter(quotes), [](auto item) {
- return std::pair{item["quote"].string_value(), false};
- });
- }
-
- auto QuotesMainWindow::buildOptionsList() -> std::list<gui::Option>
+ void QuotesMainWindow::onBeforeShow(ShowMode mode, SwitchData *data)
{
- std::list<gui::Option> optionsList;
-
- for (auto "e : quotes) {
- optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
- utils::translateI18(quote.first),
- ["e, this](gui::Item &item) {
- switchHandler(quote.second);
- return true;
- },
- [=](gui::Item &item) {
- if (item.focus) {
- this->setBottomBarText(utils::translateI18(style::strings::common::Switch),
- BottomBar::Side::CENTER);
- }
- return true;
- },
- this,
- quote.second ? gui::option::SettingRightItem::Checked : gui::option::SettingRightItem::Disabled));
- }
-
- return optionsList;
+ quotesModel->rebuild();
}
-
- void QuotesMainWindow::switchHandler(bool &optionSwitch)
- {
- optionSwitch = !optionSwitch;
- rebuildOptionList();
- }
-
- std::string QuotesMainWindow::readFileToString(const fs::path &fn)
- {
- constexpr auto tar_buf = 8192 * 4;
- auto file = std::fopen(fn.c_str(), "r");
- if (!file) {
- return {};
- }
- const auto length = utils::filesystem::filelength(file);
- if (length >= tar_buf) {
- LOG_ERROR("File %s length is too high!", fn.c_str());
- std::fclose(file);
- return {};
- }
- auto buffer = std::make_unique<char[]>(length + 1);
- std::fread(buffer.get(), 1, length, file);
- std::fclose(file);
- return std::string(buffer.get());
- }
-
} // namespace gui
M module-apps/application-settings-new/windows/QuotesMainWindow.hpp => module-apps/application-settings-new/windows/QuotesMainWindow.hpp +14 -13
@@ 4,27 4,28 @@
#pragma once
#include "BaseSettingsWindow.hpp"
+#include "application-settings-new/widgets/QuoteWidget.hpp"
+#include "application-settings-new/models/QuotesModel.hpp"
+#include <purefs/filesystem_paths.hpp>
+#include <module-gui/gui/widgets/ListView.hpp>
+#include <module-apps/InternalModel.hpp>
+#include <utility>
namespace gui
{
- class CheckBoxWithLabel;
-
- class QuotesMainWindow : public BaseSettingsWindow
+ class QuotesMainWindow : public AppWindow
{
public:
- QuotesMainWindow(app::Application *app);
-
- auto onInput(const InputEvent &inputEvent) -> bool override;
-
- protected:
- auto buildOptionsList() -> std::list<Option> override;
+ QuotesMainWindow(app::Application *app, std::shared_ptr<app::QuotesModel> model);
private:
- void readQuotes(fs::path fn);
- void switchHandler(bool &optionSwitch);
- [[nodiscard]] static std::string readFileToString(const fs::path &fn);
+ void buildInterface() override;
+ auto onInput(const InputEvent &inputEvent) -> bool override;
+ void onBeforeShow(ShowMode mode, SwitchData *data) override;
- std::list<std::pair<std::string, bool>> quotes;
+ std::shared_ptr<app::QuotesModel> quotesModel = nullptr;
+ gui::ListView *list = nullptr;
};
+
} // namespace gui
A module-apps/application-settings-new/windows/QuotesOptionsWindow.cpp => module-apps/application-settings-new/windows/QuotesOptionsWindow.cpp +85 -0
@@ 0,0 1,85 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "QuotesOptionsWindow.hpp"
+#include "OptionSetting.hpp"
+#include "application-settings-new/models/QuotesRepository.hpp"
+#include "application-settings-new/ApplicationSettings.hpp"
+#include "DialogMetadataMessage.hpp"
+#include "QuotesMainWindow.hpp"
+#include "application-settings-new/models/QuotesRepository.hpp"
+#include "application-settings-new/ApplicationSettings.hpp"
+#include "application-settings-new/widgets/QuoteWidget.hpp"
+
+#include <i18n/i18n.hpp>
+#include <widgets/Text.hpp>
+
+namespace gui
+{
+
+ QuotesOptionsWindow::QuotesOptionsWindow(app::Application *app, std::shared_ptr<app::QuotesModel> model)
+ : BaseSettingsWindow(app, gui::window::name::quotes), quotesModel(std::move(model))
+ {
+ setTitle(utils::localize.get("app_settings_display_wallpaper_quotes_options"));
+ }
+
+ auto QuotesOptionsWindow::buildOptionsList() -> std::list<gui::Option>
+ {
+ std::list<gui::Option> optionsList;
+
+ optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
+ utils::translateI18("app_settings_display_wallpaper_quotes_edit"),
+ [=](gui::Item &item) {
+ application->switchWindow(gui::window::name::new_quote,
+ std::make_unique<QuoteSwitchData>(QuoteAction::Edit, quote));
+ return true;
+ },
+ [=](gui::Item &item) {
+ if (item.focus) {
+ this->setBottomBarText(utils::translateI18(style::strings::common::select),
+ BottomBar::Side::CENTER);
+ }
+ return true;
+ },
+ this));
+
+ optionsList.emplace_back(std::make_unique<gui::option::OptionSettings>(
+ utils::translateI18("app_settings_display_wallpaper_quotes_delete"),
+ [=](gui::Item &item) {
+ gui::DialogMetadata meta;
+ meta.text = utils::localize.get("app_settings_display_wallpaper_quotes_delete_confirmation");
+ meta.title = quote.quote;
+ meta.icon = "phonebook_contact_delete_trashcan";
+ meta.action = [this]() {
+ auto backToQuotesMainWindow = 2;
+ quotesModel->remove(quote);
+ application->returnToPreviousWindow(backToQuotesMainWindow);
+ return true;
+ };
+
+ application->switchWindow(gui::window::name::quotes_dialog_yes_no,
+ std::make_unique<gui::DialogMetadataMessage>(meta));
+ return true;
+ },
+ [=](gui::Item &item) {
+ if (item.focus) {
+ this->setBottomBarText(utils::translateI18(style::strings::common::select),
+ BottomBar::Side::CENTER);
+ }
+ return true;
+ },
+ this));
+
+ return optionsList;
+ } // namespace gui
+
+ void QuotesOptionsWindow::onBeforeShow(ShowMode mode, SwitchData *data)
+ {
+ auto *quoteSwitchData = dynamic_cast<QuoteSwitchData *>(data);
+ if (quoteSwitchData != nullptr) {
+ quote = quoteSwitchData->getQuote();
+ }
+
+ BaseSettingsWindow::onBeforeShow(mode, data);
+ }
+} // namespace gui
A module-apps/application-settings-new/windows/QuotesOptionsWindow.hpp => module-apps/application-settings-new/windows/QuotesOptionsWindow.hpp +24 -0
@@ 0,0 1,24 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "BaseSettingsWindow.hpp"
+#include "QuotesMainWindow.hpp"
+#include "application-settings-new/widgets/QuoteWidget.hpp"
+
+namespace gui
+{
+ class QuotesOptionsWindow : public BaseSettingsWindow
+ {
+ public:
+ QuotesOptionsWindow(app::Application *app, std::shared_ptr<app::QuotesModel> model);
+
+ private:
+ std::list<Option> buildOptionsList() override;
+ void onBeforeShow(ShowMode mode, SwitchData *data) override;
+
+ std::shared_ptr<app::QuotesModel> quotesModel;
+ app::QuoteRecord quote;
+ };
+} // namespace gui
A module-apps/application-settings-new/windows/SystemMainWindow.cpp => module-apps/application-settings-new/windows/SystemMainWindow.cpp +37 -0
@@ 0,0 1,37 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#include "application-settings-new/ApplicationSettings.hpp"
+#include "OptionSetting.hpp"
+#include "SystemMainWindow.hpp"
+
+namespace gui
+{
+ SystemMainWindow::SystemMainWindow(app::Application *app) : BaseSettingsWindow(app, window::name::system)
+ {}
+
+ auto SystemMainWindow::buildOptionsList() -> std::list<Option>
+ {
+ std::list<Option> optionList;
+ auto addOption = [&](UTF8 name, const std::string &window) {
+ optionList.emplace_back(std::make_unique<option::OptionSettings>(
+ utils::translateI18(name),
+ [=](Item &item) {
+ LOG_INFO("switching to %s page", window.c_str());
+ application->switchWindow(window, nullptr);
+ return true;
+ },
+ nullptr,
+ nullptr,
+ option::SettingRightItem::ArrowWhite));
+ };
+
+ addOption("app_settings_language", gui::window::name::language);
+ addOption("app_settings_date_and_time", gui::window::name::date_and_time);
+ addOption("app_settings_factory_reset", gui::window::name::factory_reset);
+ addOption("app_settings_about_your_pure", gui::window::name::about_your_pure);
+ addOption("app_settings_certification", gui::window::name::certification);
+
+ return optionList;
+ }
+} // namespace gui
A module-apps/application-settings-new/windows/SystemMainWindow.hpp => module-apps/application-settings-new/windows/SystemMainWindow.hpp +18 -0
@@ 0,0 1,18 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "BaseSettingsWindow.hpp"
+
+namespace gui
+{
+ class SystemMainWindow : public BaseSettingsWindow
+ {
+ public:
+ explicit SystemMainWindow(app::Application *app);
+
+ private:
+ auto buildOptionsList() -> std::list<Option> override;
+ };
+} // namespace gui
M module-apps/application-settings/ApplicationSettings.cpp => module-apps/application-settings/ApplicationSettings.cpp +12 -8
@@ 47,16 47,10 @@ namespace app
switchWindow(app::sim_select);
return msgHandled();
});
- settings->registerValueChange(settings::SystemProperties::lockPassHash,
- [this](std::string value) { lockPassChanged(value); });
- settings->registerValueChange(settings::SystemProperties::timeDateFormat,
- [this](std::string value) { timeDateChanged(value); });
}
ApplicationSettings::~ApplicationSettings()
{
- settings->unregisterValueChange(settings::SystemProperties::lockPassHash);
- settings->unregisterValueChange(settings::SystemProperties::timeDateFormat);
}
// Invoked upon receiving data message
@@ 104,6 98,15 @@ namespace app
if (ret != sys::ReturnCodes::Success)
return ret;
+ settings->registerValueChange(
+ settings::SystemProperties::lockPassHash,
+ [this](std::string value) { lockPassChanged(value); },
+ settings::SettingsScope::Global);
+ settings->registerValueChange(
+ settings::SystemProperties::timeDateFormat,
+ [this](std::string value) { timeDateChanged(value); },
+ settings::SettingsScope::Global);
+
createUserInterface();
setActiveWindow(gui::name::window::main_window);
@@ 173,13 176,14 @@ namespace app
void ApplicationSettings::setPin(unsigned int value)
{
- settings->setValue(settings::SystemProperties::lockPassHash, std::to_string(value));
+ settings->setValue(
+ settings::SystemProperties::lockPassHash, std::to_string(value), settings::SettingsScope::Global);
lockPassHash = value;
}
void ApplicationSettings::clearPin()
{
- settings->setValue(settings::SystemProperties::lockPassHash, "");
+ settings->setValue(settings::SystemProperties::lockPassHash, "", settings::SettingsScope::Global);
lockPassHash = 0U;
}
M module-apps/application-settings/windows/BtScanWindow.cpp => module-apps/application-settings/windows/BtScanWindow.cpp +0 -2
@@ 57,8 57,6 @@ namespace gui
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
setTitle(utils::localize.get("BT_scan_results"));
M module-apps/application-settings/windows/BtWindow.cpp => module-apps/application-settings/windows/BtWindow.cpp +0 -2
@@ 59,8 59,6 @@ namespace gui
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
setTitle(utils::localize.get("app_settings_bt"));
M module-apps/application-settings/windows/CellularPassthroughWindow.cpp => module-apps/application-settings/windows/CellularPassthroughWindow.cpp +0 -2
@@ 31,8 31,6 @@ namespace gui
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
setTitle(utils::localize.get("app_settings_cellular_passthrough"));
M module-apps/application-settings/windows/CellularPassthroughWindow.hpp => module-apps/application-settings/windows/CellularPassthroughWindow.hpp +1 -3
@@ 30,8 30,6 @@ namespace gui
} // namespace cellular_passthrough
} // namespace window
- using namespace bsp::cellular::USB;
-
class CellularPassthroughWindow : public AppWindow
{
private:
@@ 76,7 74,7 @@ namespace gui
CellularPassthroughWindow::State getInitialState();
- bool set(PassthroughState pass_to_set, BootPinState dfu_to_set);
+ bool set(bsp::cellular::USB::PassthroughState pass_to_set, bsp::cellular::USB::BootPinState dfu_to_set);
void setWindowState(State state);
M module-apps/application-settings/windows/DateTimeWindow.cpp => module-apps/application-settings/windows/DateTimeWindow.cpp +0 -3
@@ 52,9 52,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
setTitle(utils::localize.get("app_settings_date_and_time"));
// create date widgets
M module-apps/application-settings/windows/EinkModeWindow.cpp => module-apps/application-settings/windows/EinkModeWindow.cpp +0 -2
@@ 27,8 27,6 @@ namespace gui
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
setTitle("Change eink mode");
auto label = new Label(this, 100, 200, 300, 50, "Change mode on click");
M module-apps/application-settings/windows/FotaWindow.cpp => module-apps/application-settings/windows/FotaWindow.cpp +0 -3
@@ 37,9 37,6 @@ namespace gui
AppWindow::buildInterface();
setTitle("Modem Firmware update (FOTA)");
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
bottomBar->setActive(BottomBar::Side::CENTER, true);
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get("Go"));
M module-apps/application-settings/windows/Info.cpp => module-apps/application-settings/windows/Info.cpp +0 -2
@@ 36,8 36,6 @@ namespace gui
AppWindow::buildInterface();
bottomBar->setActive(BottomBar::Side::RIGHT, true);
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
setTitle("Info");
M module-apps/application-settings/windows/LanguageWindow.cpp => module-apps/application-settings/windows/LanguageWindow.cpp +0 -3
@@ 49,9 49,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
setTitle(utils::localize.get("app_settings_title_languages"));
const auto &langList = loader.getAvailableDisplayLanguages();
for (const auto &lang : langList) {
M module-apps/application-settings/windows/SimSelectWindow.hpp => module-apps/application-settings/windows/SimSelectWindow.hpp +1 -1
@@ 10,4 10,4 @@ namespace app
class SimSetter;
} // namespace app
-std::list<gui::Option> simSelectWindow(app::Application *app, app::SimSetter *setter);
+std::list<gui::Option> simSelectWindow(app::Application *app, app::SimSetter *setter);<
\ No newline at end of file
M module-apps/application-settings/windows/TestMessageWindow.cpp => module-apps/application-settings/windows/TestMessageWindow.cpp +0 -3
@@ 61,9 61,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
-
receivedLabel = new gui::Label(this, 10, 50, 480 - 20, 50, "Received SMS");
receivedLabel->setAlignment(
gui::Alignment(gui::Alignment::Vertical::Center, gui::Alignment::Horizontal::Center));
M module-apps/application-special-input/windows/SpecialInputMainWindow.cpp => module-apps/application-special-input/windows/SpecialInputMainWindow.cpp +0 -2
@@ 36,8 36,6 @@ void SpecialInputMainWindow::buildInterface()
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
bottomBar->setText(BottomBar::Side::LEFT, utils::localize.get(style::strings::common::emoji));
- topBar->setActive(TopBar::Elements::TIME, true);
-
charList = new gui::ListView(this,
specialInputStyle::specialInputListView::x,
specialInputStyle::specialInputListView::y,
M module-apps/options/type/OptionSetting.hpp => module-apps/options/type/OptionSetting.hpp +1 -1
@@ 10,7 10,7 @@ namespace gui::option
{
class OptionSettings : public option::Base
{
- private:
+ protected:
UTF8 text;
std::function<bool(Item &)> activatedCallback = nullptr;
std::function<bool(Item &)> focusChangedCallback = nullptr;
M module-apps/widgets/BarGraph.cpp => module-apps/widgets/BarGraph.cpp +59 -100
@@ 18,104 18,111 @@ namespace gui
setValue(absoluteValue);
}
- Rect *BarGraph::createRectangle(uint32_t width, uint32_t height)
+ auto BarGraph::createRectangle(uint32_t width, uint32_t height) const -> Rect *
{
auto rectangle = new Rect(nullptr, 0, 0, width, height);
rectangle->setFillColor(ColorFullBlack);
rectangle->setBorderColor(ColorFullBlack);
- rectangle->setFilled(true);
+ rectangle->setFilled(false);
rectangle->setRadius(style::bargraph::radius);
rectangle->setPenWidth(style::window::default_border_focus_w);
return rectangle;
}
- Rect *BarGraph::createSpace(uint32_t width, uint32_t height)
+ auto BarGraph::createSpace(uint32_t width, uint32_t height) const -> Rect *
{
auto space = new Rect(nullptr, 0, 0, width, height);
space->setEdges(RectangleEdge::None);
return space;
}
- VBarGraph::VBarGraph(Item *parent, Position x, Position y, uint32_t numberOfRectangles)
- : VBox(parent, x, y, style::bargraph::rect_axis_length_lrg, rectAxisLenghtFrom(numberOfRectangles))
+ auto BarGraph::incrementWith(uint32_t levels) -> bool
{
- setRadius(style::bargraph::radius);
- setEdges(RectangleEdge::None);
- setMaximum(numberOfRectangles);
- std::reverse(std::begin(rectangles), std::end(rectangles));
+ if ((currentLevel + levels) <= numberOfRectangles) {
+ for (uint32_t i = 0; i < levels; ++i) {
+ rectangles[currentLevel]->setFillColor(ColorFullBlack);
+ rectangles[currentLevel]->setBorderColor(ColorFullBlack);
+ ++currentLevel;
+ }
+ return true;
+ }
+ else {
+ LOG_ERROR("bargraph incremented out of size");
+ return false;
+ }
}
- void VBarGraph::setMaximum(unsigned int value)
+ auto BarGraph::decrementWith(uint32_t levels) -> bool
{
- numberOfRectangles = value;
- setSize(rectAxisLenghtFrom(numberOfRectangles), Axis::Y);
- if (currentLevel > numberOfRectangles) {
- currentLevel = numberOfRectangles;
- }
- if (!rectangles.empty()) {
- erase();
- rectangles.clear();
+ if (currentLevel >= levels) {
+ for (uint32_t i = levels; i > 0; --i) {
+ --currentLevel;
+ rectangles[currentLevel]->setFillColor(ColorFullWhite);
+ rectangles[currentLevel]->setBorderColor(ColorFullBlack);
+ }
+ return true;
}
- for (uint32_t i = 0; i < numberOfRectangles; ++i) {
- auto rectangle =
- createRectangle(style::bargraph::rect_axis_length_lrg, style::bargraph::rect_axis_length_sml);
- addWidget(rectangle);
- rectangles.push_back(rectangle);
- addWidget(createSpace(style::bargraph::rect_axis_length_lrg, style::bargraph::spacing));
+ else {
+ LOG_ERROR("bargraph incremented out of size");
+ return false;
}
}
- void VBarGraph::update(int value)
+ auto BarGraph::update(int value) -> bool
{
if (value > 0) {
- incrementWith(value);
+ return incrementWith(value);
}
else if (value < 0) {
- decrementWith((-value));
+ return decrementWith((-value));
}
+
+ return false;
}
- void VBarGraph::setValue(unsigned int value)
+ bool BarGraph::setValue(unsigned int value)
{
if (const auto levels = static_cast<int>(value) - static_cast<int>(currentLevel); levels > 0) {
- incrementWith(levels);
+ return incrementWith(levels);
}
else if (levels < 0) {
- decrementWith(-levels);
+ return decrementWith(-levels);
}
+ return false;
}
- void VBarGraph::incrementWith(uint32_t levels)
+ VBarGraph::VBarGraph(Item *parent, Position x, Position y, uint32_t numberOfRectangles)
+ : VBox(parent, x, y, style::bargraph::rect_axis_length_lrg, rectAxisLenghtFrom(numberOfRectangles))
{
- if ((currentLevel + levels) <= numberOfRectangles) {
- for (uint32_t i = 0; i < levels; ++i) {
- rectangles[currentLevel]->setFillColor(ColorFullBlack);
- rectangles[currentLevel]->setBorderColor(ColorFullBlack);
- ++currentLevel;
- }
- }
- else {
- LOG_ERROR("bargraph incremented out of size");
- }
+ setRadius(style::bargraph::radius);
+ setEdges(RectangleEdge::None);
+ setMaximum(numberOfRectangles);
+ std::reverse(std::begin(rectangles), std::end(rectangles));
}
- void VBarGraph::decrementWith(uint32_t levels)
+ void VBarGraph::setMaximum(unsigned int value)
{
- if (currentLevel >= levels) {
- for (uint32_t i = levels; i > 0; --i) {
- --currentLevel;
- rectangles[currentLevel]->setFillColor(ColorTray);
- rectangles[currentLevel]->setBorderColor(ColorTray);
- }
+ numberOfRectangles = value;
+ setSize(rectAxisLenghtFrom(numberOfRectangles), Axis::Y);
+ if (currentLevel > numberOfRectangles) {
+ currentLevel = numberOfRectangles;
}
- else {
- LOG_ERROR("bargraph incremented out of size");
+ if (!rectangles.empty()) {
+ erase();
+ rectangles.clear();
+ }
+ for (uint32_t i = 0; i < numberOfRectangles; ++i) {
+ auto rectangle =
+ createRectangle(style::bargraph::rect_axis_length_lrg, style::bargraph::rect_axis_length_sml);
+ addWidget(rectangle);
+ rectangles.push_back(rectangle);
+ addWidget(createSpace(style::bargraph::rect_axis_length_lrg, style::bargraph::spacing));
}
}
- HBarGraph::HBarGraph(Item *parent, Position x, Position y, uint32_t numberOfRectangles)
- : HBox(parent, x, y, rectAxisLenghtFrom(numberOfRectangles), style::bargraph::rect_axis_length_lrg)
+ HBarGraph::HBarGraph(Item *parent, Position x, Position y, uint32_t numberOfRectangles) : HBox(parent)
{
+ setMinimumSize(rectAxisLenghtFrom(numberOfRectangles), style::bargraph::rect_axis_length_lrg);
setRadius(style::bargraph::radius);
setEdges(RectangleEdge::None);
setMaximum(numberOfRectangles);
@@ 141,52 148,4 @@ namespace gui
}
}
- void HBarGraph::update(int value)
- {
- if (value > 0) {
- incrementWith(value);
- }
- else if (value < 0) {
- decrementWith(-value);
- }
- }
-
- void HBarGraph::setValue(unsigned int value)
- {
- if (const auto levels = static_cast<int>(value) - static_cast<int>(currentLevel); levels > 0) {
- incrementWith(levels);
- }
- else if (levels < 0) {
- decrementWith(levels * -1);
- }
- }
-
- void HBarGraph::incrementWith(uint32_t levels)
- {
- if ((currentLevel + levels) <= numberOfRectangles) {
- for (uint32_t i = 0; i < levels; ++i) {
- rectangles[currentLevel]->setFillColor(ColorFullBlack);
- rectangles[currentLevel]->setBorderColor(ColorFullBlack);
- ++currentLevel;
- }
- }
- else {
- LOG_ERROR("bargraph incremented out of size");
- }
- }
-
- void HBarGraph::decrementWith(uint32_t levels)
- {
- if (currentLevel >= levels) {
- for (uint32_t i = levels; i > 0; --i) {
- --currentLevel;
- rectangles[currentLevel]->setFillColor(ColorFullWhite);
- rectangles[currentLevel]->setBorderColor(ColorFullBlack);
- }
- }
- else {
- LOG_ERROR("bargraph incremented out of size");
- }
- }
-
} /* namespace gui */
M module-apps/widgets/BarGraph.hpp => module-apps/widgets/BarGraph.hpp +13 -13
@@ 23,36 23,36 @@ namespace gui
uint32_t numberOfRectangles;
uint32_t currentLevel = 0;
- public:
- Rect *createRectangle(uint32_t width, uint32_t height);
+ [[nodiscard]] auto createRectangle(uint32_t width, uint32_t height) const -> Rect *;
+ [[nodiscard]] auto createSpace(uint32_t width, uint32_t height) const -> Rect *;
- Rect *createSpace(uint32_t width, uint32_t height);
+ auto incrementWith(uint32_t levels) -> bool;
+ auto decrementWith(uint32_t levels) -> bool;
+ public:
void setPercentageValue(unsigned int value) override;
+
+ [[nodiscard]] auto getValue() const -> uint32_t
+ {
+ return currentLevel;
+ }
+ auto update(int value = 1) -> bool final;
+
+ auto setValue(unsigned int value) -> bool override;
};
class VBarGraph : public VBox, public BarGraph
{
- void incrementWith(uint32_t levels);
- void decrementWith(uint32_t levels);
-
public:
VBarGraph(Item *parent = nullptr, Position x = 0, Position y = 0, uint32_t numberOfRectangles = 0);
void setMaximum(unsigned int value) final;
- void setValue(unsigned int value) final;
- void update(int value = 1) final;
};
class HBarGraph : public HBox, public BarGraph
{
- void incrementWith(uint32_t levels);
- void decrementWith(uint32_t levels);
-
public:
HBarGraph(Item *parent = nullptr, Position x = 0, Position y = 0, uint32_t numberOfRectangles = 0);
void setMaximum(unsigned int value) final;
- void setValue(unsigned int value) final;
- void update(int value = 1) final;
};
} /* namespace gui */
M module-apps/windows/AppWindow.cpp => module-apps/windows/AppWindow.cpp +16 -4
@@ 49,10 49,22 @@ namespace gui
title->setEllipsis(Ellipsis::Right);
title->visible = false;
- topBar = new gui::TopBar(this, 0, 0, 480, 50);
- topBar->setActive(TopBar::Elements::LOCK, false);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIGNAL, false);
+ auto config = configureTopBar(application->getTopBarConfiguration());
+ topBar = new gui::top_bar::TopBar(this, 0, 0, 480, 50);
+ topBar->configure(std::move(config));
+ }
+
+ top_bar::Configuration AppWindow::configureTopBar(top_bar::Configuration appConfiguration)
+ {
+ return appConfiguration;
+ }
+
+ void AppWindow::applyToTopBar(TopBarConfigurationChangeFunction configChange)
+ {
+ if (configChange) {
+ auto newConfiguration = configChange(topBar->getConfiguration());
+ topBar->configure(std::move(newConfiguration));
+ }
}
bool AppWindow::setSIM()
M module-apps/windows/AppWindow.hpp => module-apps/windows/AppWindow.hpp +21 -5
@@ 40,12 40,17 @@ namespace gui
/**
* Information bar for signal, battery and lock icon on the top of the screen.
*/
- gui::TopBar *topBar = nullptr;
+ gui::top_bar::TopBar *topBar = nullptr;
/**
* Pointer to the application object that owns the window.
*/
app::Application *application = nullptr;
+ /**
+ * A function that applies configuration changes to the current top bar configuration.
+ */
+ using TopBarConfigurationChangeFunction = std::function<top_bar::Configuration(top_bar::Configuration)>;
+
public:
AppWindow() = delete;
AppWindow(app::Application *app, std::string name);
@@ 54,10 59,7 @@ namespace gui
{
return application;
};
- void setApplication(app::Application *app)
- {
- application = app;
- };
+
virtual bool onDatabaseMessage(sys::Message *msg);
bool updateBatteryCharger(bool charging);
@@ 76,6 78,20 @@ namespace gui
void destroyInterface() override;
bool onInput(const InputEvent &inputEvent) override;
void accept(GuiVisitor &visitor) override;
+
+ /**
+ * Configure the top bar using window-specific configuration.
+ * @param appConfiguration Application-wide top bar configuration that it to be modified.
+ * @return window-specific configuration of the top bar.
+ */
+ virtual top_bar::Configuration configureTopBar(top_bar::Configuration appConfiguration);
+
+ /**
+ * Applies configuration change on the current top bar configuration.
+ * @param configChange The function that contains the top bar configuration changes.
+ */
+ void applyToTopBar(TopBarConfigurationChangeFunction configChange);
+
/// Setting bottom bar temporary text
/// @param text - bottomBar text
/// @param overwriteOthers - set or not other bottomBar texts to "" (default true)
M module-apps/windows/Dialog.cpp => module-apps/windows/Dialog.cpp +0 -6
@@ 50,7 50,6 @@ Dialog::Dialog(app::Application *app, const std::string &name) : gui::AppWindow(
{
AppWindow::buildInterface();
- topBar->setActive(TopBar::Elements::TIME, true);
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
setTitle("");
@@ 77,9 76,6 @@ void Dialog::onBeforeShow(ShowMode mode, SwitchData *data)
DialogConfirm::DialogConfirm(app::Application *app, const std::string &name) : Dialog(app, name)
{
- topBar->setActive(TopBar::Elements::BATTERY, true);
- topBar->setActive(TopBar::Elements::SIGNAL, true);
-
bottomBar->setActive(BottomBar::Side::RIGHT, false);
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::ok));
setFocusItem(icon);
@@ 169,8 165,6 @@ void DialogYesNoIconTxt::onBeforeShow(ShowMode mode, SwitchData *data)
if (auto metadata = dynamic_cast<DialogMetadataMessage *>(data); metadata != nullptr) {
DialogYesNo::onBeforeShow(mode, metadata);
iconText->setText(metadata->get().iconText);
- topBar->setActive(TopBar::Elements::BATTERY, false);
- topBar->setActive(TopBar::Elements::SIM, false);
setFocusItem(no);
}
}
M module-apps/windows/OptionWindow.cpp => module-apps/windows/OptionWindow.cpp +1 -2
@@ 63,8 63,6 @@ namespace gui
bottomBar->setText(BottomBar::Side::CENTER, utils::localize.get(style::strings::common::select));
bottomBar->setText(BottomBar::Side::RIGHT, utils::localize.get(style::strings::common::back));
- topBar->setActive(TopBar::Elements::SIGNAL, true);
- topBar->setActive(TopBar::Elements::BATTERY, true);
setTitle(name);
optionsList = new gui::ListView(this,
@@ 97,4 95,5 @@ namespace gui
resetOptions(message->takeOptions());
}
}
+
} /* namespace gui */
M module-apps/windows/OptionWindow.hpp => module-apps/windows/OptionWindow.hpp +0 -1
@@ 19,7 19,6 @@ namespace gui
class OptionWindow : public AppWindow
{
-
protected:
std::shared_ptr<OptionsModel> optionsModel = nullptr;
ListView *optionsList = nullptr;
M module-audio/Audio/StreamQueuedEventsListener.cpp => module-audio/Audio/StreamQueuedEventsListener.cpp +2 -1
@@ 5,7 5,8 @@
using namespace audio;
-StreamQueuedEventsListener::StreamQueuedEventsListener(std::shared_ptr<Queue> eventsQueue) : queue(eventsQueue)
+StreamQueuedEventsListener::StreamQueuedEventsListener(std::shared_ptr<cpp_freertos::Queue> eventsQueue)
+ : queue(eventsQueue)
{}
void StreamQueuedEventsListener::onEvent(Stream *stream, Stream::Event event, Stream::EventSourceMode source)
M module-audio/Audio/StreamQueuedEventsListener.hpp => module-audio/Audio/StreamQueuedEventsListener.hpp +2 -4
@@ 13,8 13,6 @@
namespace audio
{
- using namespace cpp_freertos;
-
class StreamQueuedEventsListener : public Stream::EventListener
{
private:
@@ 29,7 27,7 @@ namespace audio
using queuedEvent = std::pair<Stream *, Stream::Event>;
static constexpr auto listenerElementSize = sizeof(EventStorage);
- StreamQueuedEventsListener(std::shared_ptr<Queue> eventsQueue);
+ StreamQueuedEventsListener(std::shared_ptr<cpp_freertos::Queue> eventsQueue);
void onEvent(Stream *stream, Stream::Event event, Stream::EventSourceMode source);
@@ 39,7 37,7 @@ namespace audio
std::size_t getEventsCount() const;
private:
- std::shared_ptr<Queue> queue;
+ std::shared_ptr<cpp_freertos::Queue> queue;
};
}; // namespace audio
M module-bsp/board/linux/battery-charger/battery_charger.cpp => module-bsp/board/linux/battery-charger/battery_charger.cpp +81 -95
@@ 1,21 1,5 @@
-// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-
-/*
- * battery_charger.cpp
- *
- * Created on: Jul 1, 2019
- * Author: kuba
- */
-#include <stdint.h>
-
-extern "C"
-{
-#include "FreeRTOS.h"
-#include "task.h"
-#include "queue.h"
-}
-
#include <sys/stat.h>
#include <fcntl.h>
#include <module-utils/common_data/EventStore.hpp>
@@ 23,114 7,116 @@ extern "C"
#include "board.h"
#include "bsp/battery-charger/battery_charger.hpp"
-#define BSP_BATTERY_CHARGER_I2C_ADDR (0xD2 >> 1)
-#define BSP_FUEL_GAUGE_I2C_ADDR (0x6C >> 1)
-#define BSP_TOP_CONTROLLER_I2C_ADDR (0xCC >> 1)
-
-static xQueueHandle qHandleIrq = NULL;
-static TaskHandle_t battery_worker_handle = NULL;
-
-static uint8_t battLevel = 100;
-static bool plugged = false;
-namespace bsp
+namespace bsp::battery_charger
{
+ namespace
+ {
+ xQueueHandle IRQQueueHandle = nullptr;
+ TaskHandle_t batteryWorkerHandle = nullptr;
+ constexpr auto batteryFIFO = "/tmp/fifoBattKeys";
+ constexpr auto fifoFileAccessRights = 0666;
+ constexpr auto fifoBuffSize = 10;
+ constexpr auto queueTimeoutTicks = 100;
+ constexpr auto taskDelay = 50;
+
+ StateOfCharge battLevel = 100;
+ constexpr StateOfCharge fullBattery = 100;
+ bool plugged = false;
+
+ constexpr auto chargerPlugStateChange = 'p';
+ constexpr auto batteryLevelUp = ']';
+ constexpr auto batteryLevelDown = '[';
+
+ void battery_worker(void *parameters)
+ {
+ mkfifo(batteryFIFO, fifoFileAccessRights);
+
+ // Open FIFO for write only
+ int fd = open(batteryFIFO, O_RDONLY | O_NONBLOCK);
+
+ while (true) {
+ std::uint8_t buff[fifoBuffSize];
+ std::int32_t readBytes = read(fd, buff, fifoBuffSize);
+
+ if (readBytes > 0) {
+ std::uint8_t notification = 0;
+ switch (static_cast<char>(buff[0])) {
+ case chargerPlugStateChange:
+ notification = static_cast<std::uint8_t>(batteryIRQSource::INOKB);
+ plugged = !plugged;
+ break;
+ case batteryLevelUp:
+ notification = static_cast<std::uint8_t>(batteryIRQSource::INTB);
+ if (battLevel < fullBattery)
+ battLevel++;
+ else {
+ // second 100% in a row
+ if (plugged && Store::Battery::get().level == fullBattery) {
+ Store::Battery::modify().state = Store::Battery::State::PluggedNotCharging;
+ }
+ }
+ break;
+ case batteryLevelDown:
+ notification = static_cast<std::uint8_t>(batteryIRQSource::INTB);
+ if (battLevel >= 1)
+ battLevel--;
+ if (plugged && Store::Battery::get().level == fullBattery) {
+ // charging but not 100% anymore
+ Store::Battery::modify().state = Store::Battery::State::Charging;
+ }
+ break;
+ }
+ xQueueSend(IRQQueueHandle, ¬ification, queueTimeoutTicks);
+ }
+ vTaskDelay(taskDelay);
+ }
+ }
+ } // namespace
- static void battery_worker(void *pvp);
-
- int battery_Init(xQueueHandle qHandle)
+ int init(xQueueHandle queueHandle)
{
- qHandleIrq = qHandle;
- if (xTaskCreate(battery_worker, "battery", 512, qHandle, 0, &battery_worker_handle) != pdPASS) {
+ IRQQueueHandle = queueHandle;
+ if (xTaskCreate(battery_worker, "battery", 512, queueHandle, 0, &batteryWorkerHandle) != pdPASS) {
return 1;
}
Store::Battery::modify().level = battLevel;
return 0;
}
- void battery_Deinit(void)
+ void deinit()
{
- qHandleIrq = NULL;
- vTaskDelete(battery_worker_handle);
+ IRQQueueHandle = nullptr;
+ vTaskDelete(batteryWorkerHandle);
}
- void battery_getBatteryLevel(uint8_t &levelPercent)
+
+ StateOfCharge getBatteryLevel()
{
- levelPercent = battLevel;
Store::Battery::modify().level = battLevel;
+ return battLevel;
}
- void battery_getChargeStatus(bool &status)
+ bool getChargeStatus()
{
- status = plugged;
+ bool status = plugged;
if (status) {
Store::Battery::modify().state = Store::Battery::State::Charging;
}
else {
Store::Battery::modify().state = Store::Battery::State::Discharging;
}
+ return status;
}
// TODO function unused in linux driver, left for compatibility with target driver
- void battery_ClearAllIRQs(void)
+ void clearAllIRQs()
{}
// TODO function unused in linux driver, left for compatibility with target driver
- void battery_clearFuelGuageIRQ(void)
+ void clearFuelGuageIRQ()
{}
- static void battery_worker(void *pvp)
- {
-
- const char *myfifo = "/tmp/fifoBattKeys";
-
- // Creating the named file(FIFO)
- // mkfifo(<pathname>, <permission>)
- mkfifo(myfifo, 0666);
-
- // Open FIFO for write only
- int fd;
- fd = open(myfifo, O_RDONLY | O_NONBLOCK);
-
- while (1) {
- uint8_t buff[10];
- int32_t readedBytes = read(fd, buff, 10);
-
- if (readedBytes > 0) {
-
- uint8_t notification = 0;
- switch (buff[0]) {
- case 'p':
- notification = static_cast<uint8_t>(bsp::batteryIRQSource::INOKB);
- plugged = 1 - plugged;
- break;
- case ']':
- notification = static_cast<uint8_t>(bsp::batteryIRQSource::INTB);
- if (battLevel < 100)
- battLevel++;
- else {
- // second 100% in a row
- if (plugged && Store::Battery::get().level == 100) {
- Store::Battery::modify().state = Store::Battery::State::PluggedNotCharging;
- }
- }
- break;
- case '[':
- notification = static_cast<uint8_t>(bsp::batteryIRQSource::INTB);
- if (battLevel >= 1)
- battLevel--;
- if (plugged && Store::Battery::get().level == 100) {
- // charging but not 100% anymore
- Store::Battery::modify().state = Store::Battery::State::Charging;
- }
- break;
- }
- xQueueSend(qHandleIrq, ¬ification, 100);
- }
- vTaskDelay(50);
- }
- }
-
- std::uint16_t battery_getStatusRegister()
+ std::uint16_t getStatusRegister()
{
return static_cast<std::uint16_t>(batteryINTBSource::SOCOnePercentChange);
}
-} // namespace bsp
+} // namespace bsp::battery_charger
M module-bsp/board/linux/usb_cdc/usb_cdc.cpp => module-bsp/board/linux/usb_cdc/usb_cdc.cpp +1 -2
@@ 32,7 32,6 @@ namespace bsp
{
LOG_INFO("[ServiceDesktop:BSP_Driver] Start reading on fd:%d", fd);
char inputData[SERIAL_BUFFER_LEN];
- static std::string receiveMsg;
while (1) {
if (uxQueueSpacesAvailable(USBReceiveQueue) != 0) {
@@ 61,7 60,7 @@ namespace bsp
continue;
}
#endif
- receiveMsg = std::string(inputData, inputData + length);
+ std::string *receiveMsg = new std::string(inputData, inputData + length);
xQueueSend(USBReceiveQueue, &receiveMsg, portMAX_DELAY);
}
else {
A module-bsp/board/rt1051/bsp/battery-charger/MAX77818.hpp => module-bsp/board/rt1051/bsp/battery-charger/MAX77818.hpp +160 -0
@@ 0,0 1,160 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+#pragma once
+
+namespace bsp::battery_charger
+{
+
+ constexpr inline auto BATTERY_CHARGER_I2C_ADDR = 0xD2 >> 1;
+ constexpr inline auto FUEL_GAUGE_I2C_ADDR = 0x6C >> 1;
+ constexpr inline auto TOP_CONTROLLER_I2C_ADDR = 0xCC >> 1;
+
+ enum class Registers
+ {
+ TOP_CONTROLL_PMIC_ID_REG = 0x20,
+ TOP_CONTROLL_PMIC_VER_REG = 0x21,
+ TOP_CONTROLL_IRQ_SRC_REG = 0x22,
+ TOP_CONTROLL_IRQ_MASK_REG = 0x23,
+ SYSTEM_IRQ_REG = 0x24,
+
+ STATUS_REG = 0x00,
+ VALRT_Th_REG = 0x01,
+ TALRT_Th_REG = 0x02,
+ SALRT_Th_REG = 0x03,
+ AtRate_REG = 0x04,
+ RepCap_REG = 0x05,
+ RepSOC_REG = 0x06,
+ Age_REG = 0x07,
+ TEMP_REG = 0x08,
+ VCELL_REG = 0x09,
+ Current_REG = 0x0A,
+ AvgCurrent_REG = 0x0B,
+ QResidual_REG = 0x0C,
+ MixSOC_REG = 0x0D,
+ AvSOC_REG = 0x0E,
+ MixCap_REG = 0x0F,
+
+ FullCAP_REG = 0x10,
+ TTE_REG = 0x11,
+ QRtable00_REG = 0x12,
+ FullSOCthr_REG = 0x13,
+ RSLOW_REG = 0x14,
+ AvgTA_REG = 0x16,
+ Cycles_REG = 0x17,
+ DesignCap_REG = 0x18,
+ AvgVCELL_REG = 0x19,
+ MaxMinTemp_REG = 0x1A,
+ MaxMinVolt_REG = 0x1B,
+ MaxMinCurr_REG = 0x1C,
+ CONFIG_REG = 0x1D,
+ CONFIG2_REG = 0xBB,
+ ICHGTERM_REG = 0x1E,
+ AvCap_REG = 0x1F,
+
+ TTF_REG = 0x20,
+ DevName_REG = 0x21,
+ QRtable10_REG = 0x22,
+ FullCAPNom_REG = 0x23,
+ TempNom_REG = 0x24,
+ TempLim_REG = 0x25,
+ AIN0_REG = 0x27,
+ LearnCFG_REG = 0x28,
+ FilterCFG_REG = 0x29,
+ RelaxCFG_REG = 0x2A,
+ MiscCFG_REG = 0x2B,
+ TGAIN_REG = 0x2C,
+ TOFF_REG = 0x2D,
+ CGAIN_REG = 0x2E,
+ COFF_REG = 0x2F,
+
+ QRtable20_REG = 0x32,
+ AtTTF_REG = 0x33,
+ FullCapRep_REG = 0x35,
+ lavgEmpty_REG = 0x36,
+ FCTC_REG = 0x37,
+ RCOMP0_REG = 0x38,
+ TempCo_REG = 0x39,
+ VEmpty_REG = 0x3A,
+ TIMER_REG = 0x3E,
+ SHDNTIMER_REG = 0x3F,
+
+ QRtable30_REG = 0x42,
+ dQ_acc_REG = 0x45,
+ dP_acc_REG = 0x46,
+ ConvgCfg_REG = 0x49,
+ VFRemCap_REG = 0x4A,
+ QH_REG = 0x4D,
+ CHG_INT_REG = 0xb0,
+ CHG_INT_OK = 0xb2
+ };
+
+ // STATUS register bits
+ enum STATUS
+ {
+ Inm = (1 << 0),
+ POR = (1 << 1),
+ SPR_2 = (1 << 2),
+ BST = (1 << 3),
+ Isysmx = (1 << 4),
+ SPR_5 = (1 << 5),
+ ThmHot = (1 << 6),
+ dSOCi = (1 << 7),
+ Vmn = (1 << 8),
+ Tmn = (1 << 9),
+ Smn = (1 << 10),
+ Bi = (1 << 11),
+ Vmx = (1 << 12),
+ Tmx = (1 << 13),
+ Smx = (1 << 14),
+ Br = (1 << 15),
+ };
+
+ /// CHG_INT registers from documentation
+ enum class CHG_INT
+ {
+ BYP_I = (1 << 0),
+ RSVD = (1 << 1),
+ BATP_I = (1 << 2),
+ BAT_I = (1 << 3),
+ CHG_I = (1 << 4),
+ WCIN_I = (1 << 5),
+ CHGIN_I = (1 << 6),
+ AICL_I = (1 << 7),
+ };
+
+ // CONFIG register bits
+ enum class CONFIG
+ {
+ Ber = 1 << 0,
+ Bei = 1 << 1,
+ Aen = 1 << 2,
+ FTHRM = 1 << 3,
+ ETHRM = 1 << 4,
+ SPR_5 = 1 << 5,
+ I2CSH = 1 << 6,
+ SHDN = 1 << 7,
+ Tex = 1 << 8,
+ Ten = 1 << 9,
+ AINSH = 1 << 10,
+ SPR_11 = 1 << 11,
+ Vs = 1 << 12,
+ Ts = 1 << 13,
+ Ss = 1 << 14,
+ SPR_15 = 1 << 15
+ };
+
+ // CONFIG2 register bits
+ enum class CONFIG2
+ {
+ ISysNCurr = 1 << 0,
+ OCVQen = 1 << 4,
+ LdMdl = 1 << 5,
+ TAlrtEn = 1 << 6,
+ dSOCen = 1 << 7,
+ ThmHotAlrtEn = 1 << 8,
+ ThmHotEn = 1 << 9,
+ FCThmHot = 1 << 10,
+ SPR = 1 << 11
+ };
+
+} // namespace bsp::battery_charger
M module-bsp/board/rt1051/bsp/battery-charger/battery_charger.cpp => module-bsp/board/rt1051/bsp/battery-charger/battery_charger.cpp +337 -478
@@ 1,585 1,444 @@
-// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-/*
- * battery_charger.cpp
- *
- * Created on: Jun 28, 2019
- * Author: kuba
- */
-
-extern "C"
-{
-#include "FreeRTOS.h"
-#include "task.h"
-#include "queue.h"
-}
-
#include "bsp/battery-charger/battery_charger.hpp"
+#include "MAX77818.hpp"
#include "vfs.hpp"
#include "bsp/BoardDefinitions.hpp"
#include "common_data/EventStore.hpp"
#include "drivers/gpio/DriverGPIO.hpp"
#include "drivers/i2c/DriverI2C.hpp"
-#include <cstdio>
#include <purefs/filesystem_paths.hpp>
+#include <utility>
-#define BSP_BATTERY_CHARGER_I2C_ADDR (0xD2 >> 1)
-#define BSP_FUEL_GAUGE_I2C_ADDR (0x6C >> 1)
-#define BSP_TOP_CONTROLLER_I2C_ADDR (0xCC >> 1)
+namespace bsp::battery_charger
+{
+ namespace
+ {
+ constexpr std::uint32_t i2cSubaddresSize = 1;
-static const uint32_t i2cSubaddresSize = 1;
+ const auto cfgFile = purefs::dir::getCurrentOSPath() / "batteryAdjustementConfig.cfg";
+ const auto cfgFilePrev = purefs::dir::getCurrentOSPath() / "batteryAdjustementConfig_old.cfg";
-namespace configs
-{
- const auto battery_cfgFile = purefs::dir::getCurrentOSPath() / "batteryAdjustementConfig.cfg";
- const auto battery_cfgFilePrev = purefs::dir::getCurrentOSPath() / "batteryAdjustementConfig_old.cfg";
-} // namespace configs
+ constexpr std::uint16_t BATT_SERVICE_AVG_CURRENT_PERIOD =
+ 0x00; //< 0.1758 ms * 2^(2 + BATT_SERVICE_AVG_CURRENT_PERIOD) == 700ms
+ constexpr std::uint16_t BATT_SERVICE_AVG_CELL_VOLTAGE_PERIOD =
+ 0x00; //< 0.1758 ms * 2^(6 + BATT_SERVICE_AVG_CELL_VOLTAGE_PERIOD) == 11.25 s
+ constexpr std::uint16_t BATT_SERVICE_AVG_MIXING_PERIOD =
+ 0x0D; //< 0.1758 ms * 2^(5 + BATT_SERVICE_AVG_MIXING_PERIOD) == 12.8 h
+ constexpr std::uint16_t BATT_SERVICE_AVG_TEMP_PERIOD =
+ 0x01; //< 0.1758 ms * 2^(11 + BATT_SERVICE_AVG_TEMP_PERIOD) == 12 min
+ constexpr std::uint16_t BATT_SERVICE_AVG_NEMPTY_PERIOD = 0x00;
-static const uint16_t BATT_SERVICE_AVG_CURRENT_PERIOD =
- 0x00; //< 0.1758 ms * 2^(2 + BATT_SERVICE_AVG_CURRENT_PERIOD) == 700ms
-static const uint16_t BATT_SERVICE_AVG_CELL_VOLTAGE_PERIOD =
- 0x00; //< 0.1758 ms * 2^(6 + BATT_SERVICE_AVG_CELL_VOLTAGE_PERIOD) == 11.25 s
-static const uint16_t BATT_SERVICE_AVG_MIXING_PERIOD =
- 0x0D; //< 0.1758 ms * 2^(5 + BATT_SERVICE_AVG_MIXING_PERIOD) == 12.8 h
-static const uint16_t BATT_SERVICE_AVG_TEMP_PERIOD =
- 0x01; //< 0.1758 ms * 2^(11 + BATT_SERVICE_AVG_TEMP_PERIOD) == 12 min
-static const uint16_t BATT_SERVICE_AVG_NEMPTY_PERIOD = 0x00;
+ constexpr auto ENABLE_ALL_IRQ_MASK = 0xf8;
-static const uint16_t battery_nominalCapacitymAh = 3000;
+ constexpr std::uint16_t nominalCapacitymAh = 3000;
-static const uint8_t battery_fullyChargedPercent = 100;
-static const uint8_t battery_DischargedPercent = 15;
+ constexpr std::uint8_t fullyChargedPercent = 100;
+ constexpr std::uint8_t DischargedPercent = 15;
-static const uint8_t battery_maxTemperatureDegrees = 50;
-static const uint8_t battery_minTemperatureDegrees = 5;
+ constexpr std::uint8_t maxTemperatureDegrees = 50;
+ constexpr std::uint8_t minTemperatureDegrees = 5;
-static constexpr inline uint16_t battery_maxVoltagemV = 4200;
-static constexpr inline uint16_t battery_minVoltagemV = 3600;
+ constexpr std::uint16_t maxVoltagemV = 4200;
+ constexpr std::uint16_t minVoltagemV = 3600;
-using namespace drivers;
+ std::shared_ptr<drivers::DriverI2C> i2c;
+ std::shared_ptr<drivers::DriverGPIO> gpio;
-static std::shared_ptr<drivers::DriverI2C> i2c;
-static std::shared_ptr<drivers::DriverGPIO> gpio;
+ drivers::I2CAddress fuelGaugeAddress = {FUEL_GAUGE_I2C_ADDR, 0, i2cSubaddresSize};
+ drivers::I2CAddress batteryChargerAddress = {BATTERY_CHARGER_I2C_ADDR, 0, i2cSubaddresSize};
+ drivers::I2CAddress topControllerAddress = {TOP_CONTROLLER_I2C_ADDR, 0, i2cSubaddresSize};
-static bsp::batteryRetval battery_loadConfiguration(void);
+ xQueueHandle IRQQueueHandle = nullptr;
-static bsp::batteryRetval battery_storeConfiguration(void);
+ int fuelGaugeWrite(Registers registerAddress, std::uint16_t value)
+ {
+ fuelGaugeAddress.subAddress = static_cast<std::uint32_t>(registerAddress);
+ auto ret = i2c->Write(fuelGaugeAddress, reinterpret_cast<std::uint8_t *>(&value), sizeof(std::uint16_t));
-static int battery_fuelGaugeWrite(bsp::batteryChargerRegisters registerAddress, uint16_t value);
+ if (ret != sizeof(std::uint16_t)) {
+ return kStatus_Fail;
+ }
+ return kStatus_Success;
+ }
-static int battery_fuelGaugeRead(bsp::batteryChargerRegisters registerAddress, uint16_t *value);
+ std::pair<int, std::uint16_t> fuelGaugeRead(Registers registerAddress)
+ {
+ std::uint16_t value;
+ int status = kStatus_Success;
+ fuelGaugeAddress.subAddress = static_cast<std::uint32_t>(registerAddress);
+ auto ret = i2c->Read(fuelGaugeAddress, reinterpret_cast<std::uint8_t *>(&value), sizeof(std::uint16_t));
+
+ if (ret != sizeof(std::uint16_t)) {
+ status = kStatus_Fail;
+ }
+ return std::make_pair(status, value);
+ }
-static int battery_chargerWrite(bsp::batteryChargerRegisters registerAddress, uint8_t value);
+ int chargerWrite(Registers registerAddress, std::uint8_t value)
+ {
+ batteryChargerAddress.subAddress = static_cast<std::uint32_t>(registerAddress);
+ auto ret =
+ i2c->Write(batteryChargerAddress, reinterpret_cast<std::uint8_t *>(&value), sizeof(std::uint8_t));
-static int battery_chargerRead(bsp::batteryChargerRegisters registerAddress, uint8_t *value);
+ if (ret != sizeof(std::uint8_t)) {
+ return kStatus_Fail;
+ }
+ return kStatus_Success;
+ }
-static int battery_chargerTopControllerWrite(bsp::batteryChargerRegisters registerAddress, uint8_t value);
+ std::pair<int, std::uint8_t> chargerRead(Registers registerAddress)
+ {
+ std::uint8_t value;
+ int status = kStatus_Success;
+ batteryChargerAddress.subAddress = static_cast<std::uint32_t>(registerAddress);
+ auto ret = i2c->Read(batteryChargerAddress, &value, sizeof(std::uint8_t));
+
+ if (ret != sizeof(std::uint8_t)) {
+ status = kStatus_Fail;
+ }
+ return std::make_pair(status, value);
+ }
-static int battery_chargerTopControllerRead(bsp::batteryChargerRegisters registerAddress, uint8_t *value);
+ int chargerTopControllerWrite(Registers registerAddress, std::uint8_t value)
+ {
+ topControllerAddress.subAddress = static_cast<std::uint32_t>(registerAddress);
+ auto ret = i2c->Write(topControllerAddress, reinterpret_cast<std::uint8_t *>(&value), sizeof(std::uint8_t));
-static bsp::batteryRetval battery_setAvgCalcPeriods(void);
+ if (ret != sizeof(std::uint8_t)) {
+ return kStatus_Fail;
+ }
+ return kStatus_Success;
+ }
-static bsp::batteryRetval battery_setAvgCalcPeriods(void);
+ std::pair<int, std::uint8_t> chargerTopControllerRead(Registers registerAddress)
+ {
+ std::uint8_t value;
+ int status = kStatus_Success;
+ topControllerAddress.subAddress = static_cast<std::uint32_t>(registerAddress);
+ auto ret = i2c->Read(topControllerAddress, &value, sizeof(std::uint8_t));
+ if (ret != sizeof(std::uint8_t)) {
+ status = kStatus_Fail;
+ }
+ return std::make_pair(status, value);
+ }
-static bsp::batteryRetval battery_setNominalBatteryCapacity(uint16_t capacity);
+ batteryRetval loadConfiguration()
+ {
+ auto fd = std::fopen(cfgFile.c_str(), "r");
+ if (fd == nullptr) {
+ LOG_WARN("Configuration file [%s] could not be opened. Trying to open file [%s]",
+ cfgFile.c_str(),
+ cfgFilePrev.c_str());
+ fd = std::fopen(cfgFilePrev.c_str(), "r");
+ if (fd == nullptr) {
+ LOG_WARN("Configuration file [%s] could not be opened.", cfgFilePrev.c_str());
+ return batteryRetval::ChargerError;
+ }
+ }
+
+ std::uint16_t regValue = 0;
+ for (auto i = 0; i < 0xff; ++i) {
+ if (std::fread(®Value, sizeof(regValue), 1, fd) != sizeof(regValue)) {
+ LOG_ERROR("Reading register 0x%x failed.", i);
+ std::fclose(fd);
+ return batteryRetval::ChargerError;
+ }
+
+ if (fuelGaugeWrite(static_cast<Registers>(i), regValue) != kStatus_Success) {
+ LOG_ERROR("Writing register 0x%x failed.", i);
+ std::fclose(fd);
+ return batteryRetval::ChargerError;
+ }
+ }
-static bsp::batteryRetval battery_setChargingDischargingThresholds(uint8_t chargedThresholdPercent,
- uint8_t dischargedThresholdPercent);
+ std::fclose(fd);
+ return batteryRetval::OK;
+ }
-static bsp::batteryRetval battery_setTemperatureThresholds(uint8_t maxTemperatureDegrees,
- uint8_t minTemperatureDegrees);
+ batteryRetval storeConfiguration()
+ {
+ // TODO:M.P procedure below seems to crash system, it should be fixed.
+ if (ff_rename(cfgFile.c_str(), cfgFilePrev.c_str(), false) != 0) {
+ LOG_ERROR("Could not move configuration file");
+ return batteryRetval::ChargerError;
+ }
+
+ auto fd = std::fopen(cfgFile.c_str(), "w");
+ if (fd == nullptr) {
+ LOG_ERROR("Could not open configuration file");
+ return batteryRetval::ChargerError;
+ }
+
+ for (unsigned int i = 0; i < 0xff; ++i) {
+ auto regVal = fuelGaugeRead(static_cast<Registers>(i));
+ if (regVal.first != kStatus_Success) {
+ LOG_ERROR("Reading register 0x%x failed.", i);
+ std::fclose(fd);
+ return batteryRetval::ChargerError;
+ }
+
+ if (std::fwrite(®Val.second, sizeof(regVal.second), 1, fd) != sizeof(regVal.second)) {
+ LOG_ERROR("Storing register 0x%x failed.", i);
+ std::fclose(fd);
+ std::remove(cfgFile.c_str());
+ return batteryRetval::ChargerError;
+ }
+ }
-static bsp::batteryRetval battery_setServiceVoltageThresholds(uint16_t maxVoltage_mV, uint16_t minVoltage_mV);
+ std::fclose(fd);
+ return batteryRetval::OK;
+ }
-static bsp::batteryRetval battery_enableFuelGuageIRQs(void);
+ batteryRetval setAvgCalcPeriods()
+ {
+ std::uint16_t regVal = 0;
+ regVal |= (BATT_SERVICE_AVG_CURRENT_PERIOD << 0);
+ regVal |= (BATT_SERVICE_AVG_CELL_VOLTAGE_PERIOD << 4);
+ regVal |= (BATT_SERVICE_AVG_MIXING_PERIOD << 7);
+ regVal |= (BATT_SERVICE_AVG_TEMP_PERIOD << 11);
+ regVal |= (BATT_SERVICE_AVG_NEMPTY_PERIOD << 14);
+
+ if (fuelGaugeWrite(Registers::FilterCFG_REG, regVal) != kStatus_Success) {
+ LOG_ERROR("setAvgCalcPeriods failed.");
+ return batteryRetval::ChargerError;
+ }
+ return batteryRetval::OK;
+ }
-static bsp::batteryRetval battery_enableTopIRQs(void);
+ batteryRetval setNominalBatteryCapacity(std::uint16_t capacity)
+ {
+ std::uint16_t regVal = capacity * 2;
-static bsp::batteryRetval battery_configureAlerts();
+ if (fuelGaugeWrite(Registers::DesignCap_REG, regVal) != kStatus_Success) {
+ LOG_ERROR("setNominalBatteryCapacity failed.");
+ return batteryRetval::ChargerError;
+ }
+ return batteryRetval::OK;
+ }
-static void s_BSP_BatteryChargerIrqPinsInit();
+ batteryRetval setChargingDischargingThresholds(std::uint8_t chargedThresholdPercent,
+ std::uint8_t dischargedThresholdPercent)
+ {
+ uint16_t regVal = (chargedThresholdPercent << 8) | dischargedThresholdPercent;
-static xQueueHandle qHandleIrq = NULL;
+ if (fuelGaugeWrite(Registers::SALRT_Th_REG, regVal) != kStatus_Success) {
+ LOG_ERROR("setChargingDischargingThresholds failed.");
+ return batteryRetval::ChargerError;
+ }
+ return batteryRetval::OK;
+ }
-namespace bsp
-{
+ batteryRetval setTemperatureThresholds(std::uint8_t maxTemperatureDegrees, std::uint8_t minTemperatureDegrees)
+ {
+ std::uint16_t regVal = (maxTemperatureDegrees << 8) | minTemperatureDegrees;
- // STATUS register bits
- enum B_STATUS
- {
- Inm = (1 << 0),
- POR = (1 << 1),
- SPR_2 = (1 << 2),
- BST = (1 << 3),
- Isysmx = (1 << 4),
- SPR_5 = (1 << 5),
- ThmHot = (1 << 6),
- dSOCi = (1 << 7),
- Vmn = (1 << 8),
- Tmn = (1 << 9),
- Smn = (1 << 10),
- Bi = (1 << 11),
- Vmx = (1 << 12),
- Tmx = (1 << 13),
- Smx = (1 << 14),
- Br = (1 << 15),
- };
-
- /// CHG_INT registers from documentation
- enum B_CHG_INT
- {
- BYP_I = (1 << 0),
- RSVD = (1 << 1),
- BATP_I = (1 << 2),
- BAT_I = (1 << 3),
- CHG_I = (1 << 4),
- WCIN_I = (1 << 5),
- CHGIN_I = (1 << 6),
- AICL_I = (1 << 7),
- };
-
- // CONFIG register bits
- enum class B_CONFIG
- {
- Ber = 1 << 0,
- Bei = 1 << 1,
- Aen = 1 << 2,
- FTHRM = 1 << 3,
- ETHRM = 1 << 4,
- SPR_5 = 1 << 5,
- I2CSH = 1 << 6,
- SHDN = 1 << 7,
- Tex = 1 << 8,
- Ten = 1 << 9,
- AINSH = 1 << 10,
- SPR_11 = 1 << 11,
- Vs = 1 << 12,
- Ts = 1 << 13,
- Ss = 1 << 14,
- SPR_15 = 1 << 15
- };
-
- uint16_t battery_get_CHG_INT_OK();
-
- int battery_Init(xQueueHandle qHandle)
+ if (fuelGaugeWrite(Registers::TALRT_Th_REG, regVal) != kStatus_Success) {
+ LOG_ERROR("setTemperatureThresholds failed.");
+ return batteryRetval::ChargerError;
+ }
+ return batteryRetval::OK;
+ }
+
+ batteryRetval setServiceVoltageThresholds(std::uint16_t maxVoltage_mV, std::uint16_t minVoltage_mV)
+ {
+ std::uint16_t regVal = ((maxVoltage_mV / 20) << 8) | (minVoltage_mV / 20);
+
+ if (fuelGaugeWrite(Registers::VALRT_Th_REG, regVal) != kStatus_Success) {
+
+ LOG_ERROR("setServiceVoltageThresholds failed.");
+ return batteryRetval::ChargerError;
+ }
+ return batteryRetval::OK;
+ }
+
+ batteryRetval enableFuelGuageIRQs()
+ {
+ std::uint16_t regVal = static_cast<std::uint16_t>(CONFIG2::dSOCen);
+
+ if (fuelGaugeWrite(Registers::CONFIG2_REG, regVal) != kStatus_Success) {
+ LOG_ERROR("enableFuelGuageIRQs failed.");
+ return batteryRetval::ChargerError;
+ }
+
+ return batteryRetval::OK;
+ }
+
+ batteryRetval configureAlerts()
+ {
+ std::uint16_t regVal = static_cast<std::uint16_t>(CONFIG::Aen);
+
+ if (fuelGaugeWrite(Registers::CONFIG_REG, regVal) != kStatus_Success) {
+ LOG_ERROR("configureAlerts failed.");
+ return batteryRetval::ChargerError;
+ }
+
+ return batteryRetval::OK;
+ }
+
+ batteryRetval enableTopIRQs()
+ {
+ std::uint8_t val = ENABLE_ALL_IRQ_MASK;
+
+ if (chargerTopControllerWrite(Registers::TOP_CONTROLL_IRQ_MASK_REG, val) != kStatus_Success) {
+ LOG_ERROR("enableIRQs read failed.");
+ return batteryRetval::ChargerError;
+ }
+
+ return batteryRetval::OK;
+ }
+
+ void IRQPinsInit()
+ {
+ gpio =
+ drivers::DriverGPIO::Create(static_cast<drivers::GPIOInstances>(BoardDefinitions::BATTERY_CHARGER_GPIO),
+ drivers::DriverGPIOParams{});
+
+ drivers::DriverGPIOPinParams INOKBPinConfig;
+ INOKBPinConfig.dir = drivers::DriverGPIOPinParams::Direction::Input;
+ INOKBPinConfig.irqMode = drivers::DriverGPIOPinParams::InterruptMode::IntRisingOrFallingEdge;
+ INOKBPinConfig.defLogic = 0;
+ INOKBPinConfig.pin = static_cast<std::uint32_t>(BoardDefinitions::BATTERY_CHARGER_INOKB_PIN);
+ gpio->ConfPin(INOKBPinConfig);
+
+ drivers::DriverGPIOPinParams INTBPinConfig;
+ INTBPinConfig.dir = drivers::DriverGPIOPinParams::Direction::Input;
+ INTBPinConfig.irqMode = drivers::DriverGPIOPinParams::InterruptMode::IntFallingEdge;
+ INTBPinConfig.defLogic = 0;
+ INTBPinConfig.pin = static_cast<std::uint32_t>(BoardDefinitions::BATTERY_CHARGER_INTB_PIN);
+ gpio->ConfPin(INTBPinConfig);
+
+ gpio->EnableInterrupt(1 << static_cast<std::uint32_t>(BoardDefinitions::BATTERY_CHARGER_INOKB_PIN));
+ gpio->EnableInterrupt(1 << static_cast<std::uint32_t>(BoardDefinitions::BATTERY_CHARGER_INTB_PIN));
+ }
+ } // namespace
+
+ int init(xQueueHandle queueHandle)
{
- i2c = DriverI2C::Create(
- static_cast<I2CInstances>(BoardDefinitions::BATTERY_CHARGER_I2C),
- DriverI2CParams{.baudrate = static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_I2C_BAUDRATE)});
+ drivers::DriverI2CParams i2cParams;
+ i2cParams.baudrate = static_cast<std::uint32_t>(BoardDefinitions::BATTERY_CHARGER_I2C_BAUDRATE);
+ i2c = drivers::DriverI2C::Create(static_cast<drivers::I2CInstances>(BoardDefinitions::BATTERY_CHARGER_I2C),
+ i2cParams);
- qHandleIrq = qHandle;
+ IRQQueueHandle = queueHandle;
// check Power-On reset bit
- uint16_t status = 0;
- const uint16_t porMask = 0x0002;
- battery_fuelGaugeRead(bsp::batteryChargerRegisters::STATUS_REG, &status);
+ std::uint16_t status = fuelGaugeRead(Registers::STATUS_REG).second;
- if (status & porMask) {
+ if (status & static_cast<std::uint16_t>(STATUS::POR)) {
LOG_INFO("Initializing battery charger");
- battery_loadConfiguration();
- battery_setAvgCalcPeriods();
- battery_setNominalBatteryCapacity(battery_nominalCapacitymAh);
- battery_setChargingDischargingThresholds(battery_fullyChargedPercent, battery_DischargedPercent);
- battery_setTemperatureThresholds(battery_maxTemperatureDegrees, battery_minTemperatureDegrees);
- battery_setServiceVoltageThresholds(battery_maxVoltagemV, battery_minVoltagemV);
+ loadConfiguration();
+ setAvgCalcPeriods();
+ setNominalBatteryCapacity(nominalCapacitymAh);
+ setChargingDischargingThresholds(fullyChargedPercent, DischargedPercent);
+ setTemperatureThresholds(maxTemperatureDegrees, minTemperatureDegrees);
+ setServiceVoltageThresholds(maxVoltagemV, minVoltagemV);
}
- battery_configureAlerts();
- battery_enableFuelGuageIRQs();
+ configureAlerts();
+ enableFuelGuageIRQs();
- uint8_t level = 0;
- bool charging = false;
- battery_getBatteryLevel(level);
- battery_getChargeStatus(charging);
+ StateOfCharge level = getBatteryLevel();
+ bool charging = getChargeStatus();
LOG_INFO("Phone battery start state: %d %d", level, charging);
- battery_ClearAllIRQs();
- battery_enableTopIRQs();
+ clearAllIRQs();
+ enableTopIRQs();
- s_BSP_BatteryChargerIrqPinsInit();
+ IRQPinsInit();
return 0;
}
- void battery_Deinit(void)
+ void deinit()
{
- battery_storeConfiguration();
+ storeConfiguration();
gpio->DisableInterrupt(1 << static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_INTB_PIN));
gpio->DisableInterrupt(1 << static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_INOKB_PIN));
- gpio->DisableInterrupt(1 << static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_WCINOKB));
- qHandleIrq = NULL;
+ IRQQueueHandle = nullptr;
i2c.reset();
gpio.reset();
}
- void battery_getBatteryLevel(uint8_t &levelPercent)
+ StateOfCharge getBatteryLevel()
{
- uint16_t val = 0;
- if (battery_fuelGaugeRead(bsp::batteryChargerRegisters::RepSOC_REG, &val) != kStatus_Success) {
+ auto readout = fuelGaugeRead(Registers::RepSOC_REG);
+ if (readout.first != kStatus_Success) {
LOG_ERROR("failed to get battery percent");
}
- levelPercent = (val & 0xff00) >> 8;
+ StateOfCharge levelPercent = (readout.second & 0xff00) >> 8;
Store::Battery::modify().level = levelPercent;
+ return levelPercent;
}
- void battery_getChargeStatus(bool &status)
+ bool getChargeStatus()
{
- uint8_t val = 0;
+ std::uint8_t val = 0;
// read clears state
- if (battery_chargerRead(bsp::batteryChargerRegisters::CHG_INT_OK, &val) != kStatus_Success) {
+ auto value = chargerRead(Registers::CHG_INT_OK);
+ if (value.first != kStatus_Success) {
LOG_ERROR("failed to read charge status");
}
- status = val & B_CHG_INT::CHGIN_I;
+ bool status = value.second & static_cast<std::uint8_t>(CHG_INT::CHGIN_I);
if (status) {
Store::Battery::modify().state = Store::Battery::State::Charging;
}
else {
Store::Battery::modify().state = Store::Battery::State::Discharging;
}
+ return status;
}
- std::uint16_t battery_getStatusRegister()
+ std::uint16_t getStatusRegister()
{
- uint16_t status = 0;
- battery_fuelGaugeRead(bsp::batteryChargerRegisters::STATUS_REG, &status);
- return status;
+ auto status = fuelGaugeRead(Registers::STATUS_REG);
+ return status.second;
}
- void battery_ClearAllIRQs(void)
+ void clearAllIRQs()
{
- uint8_t val = 0;
- battery_chargerRead(bsp::batteryChargerRegisters::CHG_INT_REG, &val);
- if (val != 0) {
+ auto value = chargerRead(Registers::CHG_INT_REG);
+ if (value.second != 0) {
// write zero to clear irq source
- battery_chargerWrite(bsp::batteryChargerRegisters::CHG_INT_REG, 0);
+ chargerWrite(Registers::CHG_INT_REG, 0);
}
- uint16_t status = battery_getStatusRegister();
+ std::uint16_t status = getStatusRegister();
if (status != 0) {
// write zero to clear irq source
- battery_fuelGaugeWrite(bsp::batteryChargerRegisters::STATUS_REG, 0);
+ fuelGaugeWrite(Registers::STATUS_REG, 0);
}
}
- void battery_clearFuelGuageIRQ(void)
+ void clearFuelGuageIRQ()
{
// write zero to clear interrupt source
- battery_fuelGaugeWrite(bsp::batteryChargerRegisters::STATUS_REG, 0x0000);
+ fuelGaugeWrite(Registers::STATUS_REG, 0x0000);
}
-} // namespace bsp
-
-static int battery_fuelGaugeWrite(bsp::batteryChargerRegisters registerAddress, uint16_t value)
-{
- I2CAddress addr{.deviceAddress = BSP_FUEL_GAUGE_I2C_ADDR,
- .subAddress = static_cast<uint32_t>(registerAddress),
- .subAddressSize = i2cSubaddresSize};
- auto ret = i2c->Write(addr, reinterpret_cast<uint8_t *>(&value), sizeof(uint16_t));
-
- if (ret != sizeof(uint16_t)) {
- return kStatus_Fail;
- }
- else {
- return kStatus_Success;
- }
-}
-
-static int battery_fuelGaugeRead(bsp::batteryChargerRegisters registerAddress, uint16_t *value)
-{
- if (value == NULL) {
- return -1;
- }
-
- I2CAddress addr{.deviceAddress = BSP_FUEL_GAUGE_I2C_ADDR,
- .subAddress = static_cast<uint32_t>(registerAddress),
- .subAddressSize = i2cSubaddresSize};
- auto ret = i2c->Read(addr, reinterpret_cast<uint8_t *>(value), sizeof(uint16_t));
-
- if (ret != sizeof(uint16_t)) {
- return kStatus_Fail;
- }
- else {
- return kStatus_Success;
- }
-}
-
-static int battery_chargerWrite(bsp::batteryChargerRegisters registerAddress, uint8_t value)
-{
-
- I2CAddress addr{.deviceAddress = BSP_BATTERY_CHARGER_I2C_ADDR,
- .subAddress = static_cast<uint32_t>(registerAddress),
- .subAddressSize = i2cSubaddresSize};
- auto ret = i2c->Write(addr, reinterpret_cast<uint8_t *>(&value), sizeof(uint8_t));
-
- if (ret != sizeof(uint8_t)) {
- return kStatus_Fail;
- }
- else {
- return kStatus_Success;
- }
-}
-
-static int battery_chargerRead(bsp::batteryChargerRegisters registerAddress, uint8_t *value)
-{
- if (value == NULL) {
- return -1;
- }
-
- I2CAddress addr{.deviceAddress = BSP_BATTERY_CHARGER_I2C_ADDR,
- .subAddress = static_cast<uint32_t>(registerAddress),
- .subAddressSize = i2cSubaddresSize};
- auto ret = i2c->Read(addr, value, sizeof(uint8_t));
- if (ret != sizeof(uint8_t)) {
- return kStatus_Fail;
- }
- else {
- return kStatus_Success;
- }
-}
-
-static int battery_chargerTopControllerWrite(bsp::batteryChargerRegisters registerAddress, uint8_t value)
-{
-
- I2CAddress addr{.deviceAddress = BSP_TOP_CONTROLLER_I2C_ADDR,
- .subAddress = static_cast<uint32_t>(registerAddress),
- .subAddressSize = i2cSubaddresSize};
- auto ret = i2c->Write(addr, reinterpret_cast<uint8_t *>(&value), sizeof(uint8_t));
- if (ret != sizeof(uint8_t)) {
- return kStatus_Fail;
- }
- else {
- return kStatus_Success;
- }
-}
-
-static int battery_chargerTopControllerRead(bsp::batteryChargerRegisters registerAddress, uint8_t *value)
-{
- if (value == NULL) {
- return -1;
- }
-
- I2CAddress addr{.deviceAddress = BSP_TOP_CONTROLLER_I2C_ADDR,
- .subAddress = static_cast<uint32_t>(registerAddress),
- .subAddressSize = i2cSubaddresSize};
- auto ret = i2c->Read(addr, reinterpret_cast<uint8_t *>(value), sizeof(uint8_t));
- if (ret != sizeof(uint8_t)) {
- return kStatus_Fail;
- }
- else {
- return kStatus_Success;
- }
-}
-
-static bsp::batteryRetval battery_loadConfiguration(void)
-{
- auto fd = std::fopen(configs::battery_cfgFile.c_str(), "r");
- if (fd == NULL) {
- LOG_WARN("Configuration file [%s] not found. Searching for file [%s]",
- configs::battery_cfgFile.c_str(),
- configs::battery_cfgFilePrev.c_str());
- fd = std::fopen(configs::battery_cfgFilePrev.c_str(), "r");
- if (fd == NULL) {
- LOG_WARN("Configuration file [%s] not found.", configs::battery_cfgFilePrev.c_str());
- return bsp::batteryRetval::battery_ChargerError;
- }
- }
-
- uint16_t regValue = 0;
- for (uint8_t i = 0; i < 0xff; ++i) {
- if (std::fread(®Value, sizeof(regValue), 1, fd) != sizeof(regValue)) {
- LOG_ERROR("Reading register 0x%x failed.", i);
- std::fclose(fd);
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- if (battery_fuelGaugeWrite(static_cast<bsp::batteryChargerRegisters>(i), regValue) != kStatus_Success) {
- LOG_ERROR("Writing register 0x%x failed.", i);
- std::fclose(fd);
- return bsp::batteryRetval::battery_ChargerError;
+ BaseType_t INOKB_IRQHandler()
+ {
+ BaseType_t xHigherPriorityTaskWoken = pdFALSE;
+ if (IRQQueueHandle != nullptr) {
+ std::uint8_t val = static_cast<std::uint8_t>(batteryIRQSource::INOKB);
+ xQueueSendFromISR(IRQQueueHandle, &val, &xHigherPriorityTaskWoken);
}
+ return xHigherPriorityTaskWoken;
}
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_storeConfiguration(void)
-{
- // TODO:M.P procedure below seems to crash system, it should be fixed.
- if (ff_rename(configs::battery_cfgFile.c_str(), configs::battery_cfgFilePrev.c_str(), false) != 0) {
- LOG_ERROR("Could not move configuration file");
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- auto fd = std::fopen(configs::battery_cfgFile.c_str(), "w");
- if (fd == NULL) {
- LOG_ERROR("Could not open configuration file");
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- uint16_t regVal = 0;
- for (unsigned int i = 0; i < 0xff; ++i) {
- if (battery_fuelGaugeRead(static_cast<bsp::batteryChargerRegisters>(i), ®Val) != kStatus_Success) {
- LOG_ERROR("Reading register 0x%x failed.", i);
- std::fclose(fd);
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- if (std::fwrite(®Val, sizeof(regVal), 1, fd) != sizeof(regVal)) {
- LOG_ERROR("Storing register 0x%x failed.", i);
- std::fclose(fd);
- std::remove(configs::battery_cfgFile.c_str());
- return bsp::batteryRetval::battery_ChargerError;
+ BaseType_t INTB_IRQHandler()
+ {
+ BaseType_t xHigherPriorityTaskWoken = pdFALSE;
+ if (IRQQueueHandle != nullptr) {
+ std::uint8_t val = static_cast<std::uint8_t>(batteryIRQSource::INTB);
+ xQueueSendFromISR(IRQQueueHandle, &val, &xHigherPriorityTaskWoken);
}
+ return xHigherPriorityTaskWoken;
}
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_setAvgCalcPeriods(void)
-{
- uint16_t regVal = 0;
- regVal |= (BATT_SERVICE_AVG_CURRENT_PERIOD << 0);
- regVal |= (BATT_SERVICE_AVG_CELL_VOLTAGE_PERIOD << 4);
- regVal |= (BATT_SERVICE_AVG_MIXING_PERIOD << 7);
- regVal |= (BATT_SERVICE_AVG_TEMP_PERIOD << 11);
- regVal |= (BATT_SERVICE_AVG_NEMPTY_PERIOD << 14);
-
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::FilterCFG_REG, regVal) != kStatus_Success) {
- LOG_ERROR("battery_setAvgCalcPeriods failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_setNominalBatteryCapacity(uint16_t capacity)
-{
- uint16_t regVal = capacity * 2;
-
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::DesignCap_REG, regVal) != kStatus_Success) {
- LOG_ERROR("battery_setNominalBatteryCapacity failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_setChargingDischargingThresholds(uint8_t chargedThresholdPercent,
- uint8_t dischargedThresholdPercent)
-{
- uint16_t regVal = (chargedThresholdPercent << 8) | dischargedThresholdPercent;
-
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::SALRT_Th_REG, regVal) != kStatus_Success) {
- LOG_ERROR("battery_setChargingDischargingThresholds failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_setTemperatureThresholds(uint8_t maxTemperatureDegrees, uint8_t minTemperatureDegrees)
-{
- uint16_t regVal = (maxTemperatureDegrees << 8) | minTemperatureDegrees;
-
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::TALRT_Th_REG, regVal) != kStatus_Success) {
- LOG_ERROR("battery_setTemperatureThresholds failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_setServiceVoltageThresholds(uint16_t maxVoltage_mV, uint16_t minVoltage_mV)
-{
- uint16_t regVal = ((maxVoltage_mV / 20) << 8) | (minVoltage_mV / 20);
-
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::VALRT_Th_REG, regVal) != kStatus_Success) {
-
- LOG_ERROR("battery_setServiceVoltageThresholds failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_enableFuelGuageIRQs(void)
-{
- uint16_t regVal = 0;
- // set dSOCen bit
- regVal |= (1 << 7);
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::CONFIG2_REG, regVal) != kStatus_Success) {
- LOG_ERROR("battery_enableFuelGuageIRQs failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_configureAlerts()
-{
- auto regVal = static_cast<std::uint16_t>(bsp::B_CONFIG::Aen); // Enable alerts
-
- if (battery_fuelGaugeWrite(bsp::batteryChargerRegisters::CONFIG_REG, regVal) != kStatus_Success) {
- LOG_ERROR("battery_configureAlerts failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- return bsp::batteryRetval::battery_OK;
-}
-
-static bsp::batteryRetval battery_enableTopIRQs(void)
-{
- uint8_t val = 0xf8;
-
- if (battery_chargerTopControllerWrite(bsp::batteryChargerRegisters::TOP_CONTROLL_IRQ_MASK_REG, val) !=
- kStatus_Success) {
- LOG_ERROR("battery_enableIRQs read failed.");
- return bsp::batteryRetval::battery_ChargerError;
- }
-
- return bsp::batteryRetval::battery_OK;
-}
-
-BaseType_t BSP_BatteryChargerINOKB_IRQHandler()
-{
- BaseType_t xHigherPriorityTaskWoken = pdFALSE;
- if (qHandleIrq != NULL) {
- uint8_t val = static_cast<uint8_t>(bsp::batteryIRQSource::INOKB);
- xQueueSendFromISR(qHandleIrq, &val, &xHigherPriorityTaskWoken);
- }
- return xHigherPriorityTaskWoken;
-}
-
-BaseType_t BSP_BatteryChargerINTB_IRQHandler()
-{
- BaseType_t xHigherPriorityTaskWoken = pdFALSE;
- if (qHandleIrq != NULL) {
- uint8_t val = static_cast<uint8_t>(bsp::batteryIRQSource::INTB);
- xQueueSendFromISR(qHandleIrq, &val, &xHigherPriorityTaskWoken);
- }
- return xHigherPriorityTaskWoken;
-}
-
-static void s_BSP_BatteryChargerIrqPinsInit()
-{
-
- gpio = DriverGPIO::Create(static_cast<GPIOInstances>(BoardDefinitions::BATTERY_CHARGER_GPIO), DriverGPIOParams{});
-
- gpio->ConfPin(DriverGPIOPinParams{.dir = DriverGPIOPinParams::Direction::Input,
- .irqMode = DriverGPIOPinParams::InterruptMode::IntRisingOrFallingEdge,
- .defLogic = 0,
- .pin = static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_INOKB_PIN)});
-
- gpio->ConfPin(DriverGPIOPinParams{.dir = DriverGPIOPinParams::Direction::Input,
- .irqMode = DriverGPIOPinParams::InterruptMode::IntRisingOrFallingEdge,
- .defLogic = 0,
- .pin = static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_WCINOKB)});
-
- gpio->ConfPin(DriverGPIOPinParams{.dir = DriverGPIOPinParams::Direction::Input,
- .irqMode = DriverGPIOPinParams::InterruptMode::IntFallingEdge,
- .defLogic = 0,
- .pin = static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_INTB_PIN)});
- gpio->EnableInterrupt(1 << static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_WCINOKB));
- gpio->EnableInterrupt(1 << static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_INOKB_PIN));
- gpio->EnableInterrupt(1 << static_cast<uint32_t>(BoardDefinitions::BATTERY_CHARGER_INTB_PIN));
-}
+} // namespace bsp::battery_charger
M module-bsp/board/rt1051/common/irq/irq_gpio.cpp => module-bsp/board/rt1051/common/irq/irq_gpio.cpp +2 -3
@@ 19,7 19,6 @@
#if 0 // TODO:M.P implement the rest of BSP drivers
#include "bsp_cellular.h"
-#include "bsp_battery_charger.h"
#include "bsp_usbc.h"
#include "log.h"
@@ 114,13 113,13 @@ namespace bsp
}
if (irq_mask & (1 << BOARD_BATTERY_CHARGER_INOKB_PIN)) {
- xHigherPriorityTaskWoken |= BSP_BatteryChargerINOKB_IRQHandler();
+ xHigherPriorityTaskWoken |= bsp::battery_charger::INOKB_IRQHandler();
}
if (irq_mask & (1 << BOARD_BATTERY_CHARGER_WCINOKB_PIN)) {}
if (irq_mask & (1 << BOARD_BATTERY_CHARGER_INTB_PIN)) {
- xHigherPriorityTaskWoken |= BSP_BatteryChargerINTB_IRQHandler();
+ xHigherPriorityTaskWoken |= bsp::battery_charger::INTB_IRQHandler();
}
if (irq_mask & (1 << BSP_CELLULAR_SIM_TRAY_INSERTED_PIN)) {
M module-bsp/bsp/battery-charger/battery_charger.hpp => module-bsp/bsp/battery-charger/battery_charger.hpp +28 -102
@@ 1,99 1,25 @@
-/*
- * battery_charger.hpp
- *
- * Created on: Jun 28, 2019
- * Author: kuba
- */
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-#ifndef MODULE_BSP_BSP_BATTERY_CHARGER_BATTERY_CHARGER_HPP_
-#define MODULE_BSP_BSP_BATTERY_CHARGER_BATTERY_CHARGER_HPP_
+#pragma once
#include <cstdint>
-namespace bsp{
-
- enum class batteryChargerRegisters{
- TOP_CONTROLL_PMIC_ID_REG = 0x20,
- TOP_CONTROLL_PMIC_VER_REG = 0x21,
- TOP_CONTROLL_IRQ_SRC_REG = 0x22,
- TOP_CONTROLL_IRQ_MASK_REG = 0x23,
- SYSTEM_IRQ_REG = 0x24,
-
- STATUS_REG = 0x00,
- VALRT_Th_REG = 0x01,
- TALRT_Th_REG = 0x02,
- SALRT_Th_REG = 0x03,
- AtRate_REG = 0x04,
- RepCap_REG = 0x05,
- RepSOC_REG = 0x06,
- Age_REG = 0x07,
- TEMP_REG = 0x08,
- VCELL_REG = 0x09,
- Current_REG = 0x0A,
- AvgCurrent_REG = 0x0B,
- QResidual_REG = 0x0C,
- MixSOC_REG = 0x0D,
- AvSOC_REG = 0x0E,
- MixCap_REG = 0x0F,
-
- FullCAP_REG = 0x10,
- TTE_REG = 0x11,
- QRtable00_REG = 0x12,
- FullSOCthr_REG = 0x13,
- RSLOW_REG = 0x14,
- AvgTA_REG = 0x16,
- Cycles_REG = 0x17,
- DesignCap_REG = 0x18,
- AvgVCELL_REG = 0x19,
- MaxMinTemp_REG = 0x1A,
- MaxMinVolt_REG = 0x1B,
- MaxMinCurr_REG = 0x1C,
- CONFIG_REG = 0x1D,
- CONFIG2_REG = 0xBB,
- ICHGTERM_REG = 0x1E,
- AvCap_REG = 0x1F,
-
- TTF_REG = 0x20,
- DevName_REG = 0x21,
- QRtable10_REG = 0x22,
- FullCAPNom_REG = 0x23,
- TempNom_REG = 0x24,
- TempLim_REG = 0x25,
- AIN0_REG = 0x27,
- LearnCFG_REG = 0x28,
- FilterCFG_REG = 0x29,
- RelaxCFG_REG = 0x2A,
- MiscCFG_REG = 0x2B,
- TGAIN_REG = 0x2C,
- TOFF_REG = 0x2D,
- CGAIN_REG = 0x2E,
- COFF_REG = 0x2F,
-
- QRtable20_REG = 0x32,
- AtTTF_REG = 0x33,
- FullCapRep_REG = 0x35,
- lavgEmpty_REG = 0x36,
- FCTC_REG = 0x37,
- RCOMP0_REG = 0x38,
- TempCo_REG = 0x39,
- VEmpty_REG = 0x3A,
- TIMER_REG = 0x3E,
- SHDNTIMER_REG = 0x3F,
-
- QRtable30_REG = 0x42,
- dQ_acc_REG = 0x45,
- dP_acc_REG = 0x46,
- ConvgCfg_REG = 0x49,
- VFRemCap_REG = 0x4A,
- QH_REG = 0x4D,
- CHG_INT_REG = 0xb0,
- CHG_INT_OK = 0xb2
- };
+extern "C"
+{
+#include "FreeRTOS.h"
+#include "task.h"
+#include "queue.h"
+}
+
+namespace bsp::battery_charger
+{
+ using StateOfCharge = std::uint8_t;
enum class batteryRetval{
- battery_OK = 0,
- battery_ChargerError,
- battery_ChargerNotCharging,
- battery_ChargerCharging
+ OK,
+ ChargerError,
+ ChargerNotCharging,
+ ChargerCharging
};
enum class batteryIRQSource{
@@ 107,24 33,24 @@ namespace bsp{
SOCOnePercentChange = 1 << 7
};
- int battery_Init(xQueueHandle qHandle);
+ int init(xQueueHandle queueHandle);
- void battery_Deinit(void);
+ void deinit();
- void battery_getBatteryLevel(uint8_t& levelPercent);
+ StateOfCharge getBatteryLevel();
- void battery_getChargeStatus( bool& status);
+ bool getChargeStatus();
- void battery_ClearAllIRQs(void);
+ void clearAllIRQs();
- void battery_clearFuelGuageIRQ(void);
+ void clearFuelGuageIRQ();
- std::uint16_t battery_getStatusRegister();
-}
+ std::uint16_t getStatusRegister();
+
+ BaseType_t INOKB_IRQHandler();
-BaseType_t BSP_BatteryChargerINOKB_IRQHandler();
+ BaseType_t INTB_IRQHandler();
+} // bsp::battery_charger
-BaseType_t BSP_BatteryChargerINTB_IRQHandler();
-#endif /* MODULE_BSP_BSP_BATTERY_CHARGER_BATTERY_CHARGER_HPP_*/
M module-db/Common/Query.cpp => module-db/Common/Query.cpp +1 -1
@@ 21,7 21,7 @@ bool QueryCallback::handleQueryResponse(QueryResult *response)
return callback(response);
}
-EndpointListener::EndpointListener(EndpointQueryCallbackFunction &&_callback, Context &_context)
+EndpointListener::EndpointListener(EndpointQueryCallbackFunction &&_callback, parserFSM::Context &_context)
: callback{std::move(_callback)}, context{_context}
{}
M module-db/Common/Query.hpp => module-db/Common/Query.hpp +3 -5
@@ 9,13 9,11 @@
#include <log/log.hpp>
#include <module-services/service-desktop/endpoints/Context.hpp>
-using namespace parserFSM;
-
namespace db
{
class QueryResult; // Forward declaration
using QueryCallbackFunction = std::function<bool(db::QueryResult *)>;
- using EndpointQueryCallbackFunction = std::function<bool(db::QueryResult *, Context &)>;
+ using EndpointQueryCallbackFunction = std::function<bool(db::QueryResult *, parserFSM::Context &)>;
class QueryListener
{
@@ 42,13 40,13 @@ namespace db
{
public:
EndpointListener() = default;
- EndpointListener(EndpointQueryCallbackFunction &&_callback, Context &_context);
+ EndpointListener(EndpointQueryCallbackFunction &&_callback, parserFSM::Context &_context);
bool handleQueryResponse(db::QueryResult *result) override;
private:
EndpointQueryCallbackFunction callback;
- Context context;
+ parserFSM::Context context;
};
/// virtual query input interface
M module-db/Interface/AlarmsRecord.hpp => module-db/Interface/AlarmsRecord.hpp +1 -1
@@ 28,7 28,7 @@ namespace db::query::alarms
struct AlarmsRecord : public Record
{
- TimePoint time = TIME_POINT_INVALID;
+ calendar::TimePoint time = TIME_POINT_INVALID;
uint32_t snooze = 0;
AlarmStatus status = AlarmStatus::On;
uint32_t repeat = 0;
M module-db/Interface/EventsRecord.cpp => module-db/Interface/EventsRecord.cpp +5 -4
@@ 70,8 70,8 @@ bool EventsRecordInterface::Add(const EventsRecord &rec)
return false;
}
-std::vector<EventsRecord> EventsRecordInterface::Select(TimePoint filter_from,
- TimePoint filter_till,
+std::vector<EventsRecord> EventsRecordInterface::Select(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till,
uint32_t offset,
uint32_t limit)
{
@@ 265,12 265,13 @@ uint32_t EventsRecordInterface::GetCount()
return eventsDb->events.count();
}
-uint32_t EventsRecordInterface::GetCountFiltered(TimePoint from, TimePoint till)
+uint32_t EventsRecordInterface::GetCountFiltered(calendar::TimePoint from, calendar::TimePoint till)
{
return eventsDb->events.countFromFilter(from, till);
}
-std::vector<EventsRecord> EventsRecordInterface::SelectFirstUpcoming(TimePoint filter_from, TimePoint filter_till)
+std::vector<EventsRecord> EventsRecordInterface::SelectFirstUpcoming(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till)
{
auto rows = eventsDb->events.SelectFirstUpcoming(filter_from, filter_till);
M module-db/Interface/EventsRecord.hpp => module-db/Interface/EventsRecord.hpp +9 -6
@@ 41,11 41,11 @@ struct EventsRecord : public Record
{
std::string UID;
std::string title;
- TimePoint date_from;
- TimePoint date_till;
+ calendar::TimePoint date_from;
+ calendar::TimePoint date_till;
uint32_t reminder = 0;
uint32_t repeat = 0;
- TimePoint reminder_fired;
+ calendar::TimePoint reminder_fired;
std::string provider_type;
std::string provider_id;
std::string provider_iCalUid;
@@ 77,15 77,18 @@ class EventsRecordInterface : public RecordInterface<EventsRecord, EventsRecordF
EventsRecord GetByID(uint32_t id) override final;
EventsRecord GetByUID(const std::string &uid);
uint32_t GetCount() override final;
- uint32_t GetCountFiltered(TimePoint from, TimePoint till);
- std::vector<EventsRecord> Select(TimePoint filter_from, TimePoint filter_till, uint32_t offset, uint32_t limit);
+ uint32_t GetCountFiltered(calendar::TimePoint from, calendar::TimePoint till);
+ std::vector<EventsRecord> Select(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till,
+ uint32_t offset,
+ uint32_t limit);
std::unique_ptr<std::vector<EventsRecord>> GetLimitOffset(uint32_t offset, uint32_t limit) override final;
std::unique_ptr<std::vector<EventsRecord>> GetLimitOffsetByField(uint32_t offset,
uint32_t limit,
EventsRecordField field,
const char *str) override final;
std::vector<EventsRecord> GetLimitOffsetByDate(uint32_t offset, uint32_t limit);
- std::vector<EventsRecord> SelectFirstUpcoming(TimePoint filter_from, TimePoint filter_till);
+ std::vector<EventsRecord> SelectFirstUpcoming(calendar::TimePoint filter_from, calendar::TimePoint filter_till);
std::unique_ptr<db::QueryResult> runQuery(std::shared_ptr<db::Query> query) override;
M module-db/Tables/AlarmsTable.cpp => module-db/Tables/AlarmsTable.cpp +1 -1
@@ 9,7 9,7 @@ AlarmsTableRow::AlarmsTableRow(const AlarmsRecord &rec)
{}
AlarmsTableRow::AlarmsTableRow(
- uint32_t id, TimePoint time, uint32_t snooze, AlarmStatus status, uint32_t repeat, UTF8 path)
+ uint32_t id, calendar::TimePoint time, uint32_t snooze, AlarmStatus status, uint32_t repeat, UTF8 path)
: Record{id}, time{time}, snooze{snooze}, status{status}, repeat{repeat}, path{std::move(path)}
{}
M module-db/Tables/AlarmsTable.hpp => module-db/Tables/AlarmsTable.hpp +3 -2
@@ 25,14 25,15 @@ enum class AlarmStatus
struct AlarmsTableRow : public Record
{
- TimePoint time = TIME_POINT_INVALID;
+ calendar::TimePoint time = TIME_POINT_INVALID;
uint32_t snooze = 0;
AlarmStatus status = AlarmStatus::On;
uint32_t repeat = 0;
UTF8 path;
AlarmsTableRow() = default;
- AlarmsTableRow(uint32_t id, TimePoint time, uint32_t snooze, AlarmStatus status, uint32_t repeat, UTF8 path);
+ AlarmsTableRow(
+ uint32_t id, calendar::TimePoint time, uint32_t snooze, AlarmStatus status, uint32_t repeat, UTF8 path);
explicit AlarmsTableRow(const AlarmsRecord &rec);
explicit AlarmsTableRow(const QueryResult &result);
};
M module-db/Tables/EventsTable.cpp => module-db/Tables/EventsTable.cpp +5 -4
@@ 643,8 643,8 @@ EventsTableRow EventsTable::getByUID(const std::string &UID)
};
}
-std::vector<EventsTableRow> EventsTable::selectByDatePeriod(TimePoint date_filter,
- TimePoint filter_till,
+std::vector<EventsTableRow> EventsTable::selectByDatePeriod(calendar::TimePoint date_filter,
+ calendar::TimePoint filter_till,
uint32_t offset,
uint32_t limit)
{
@@ 770,7 770,7 @@ uint32_t EventsTable::count()
return (*queryRet)[0].getUInt32();
}
-uint32_t EventsTable::countFromFilter(TimePoint from, TimePoint till)
+uint32_t EventsTable::countFromFilter(calendar::TimePoint from, calendar::TimePoint till)
{
auto queryRet = db->query(
"SELECT COUNT(*) FROM events WHERE date_from >= date('%q') AND date_from < date('%q', 'start of day');",
@@ 791,7 791,8 @@ uint32_t EventsTable::countByFieldId(const char *field, uint32_t id)
return 0;
}
-std::vector<EventsTableRow> EventsTable::SelectFirstUpcoming(TimePoint filter_from, TimePoint filter_till)
+std::vector<EventsTableRow> EventsTable::SelectFirstUpcoming(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till)
{
auto retQuery = db->query("SELECT DATETIME(date_from, '-' || reminder || ' minutes') AS calc_dt, * "
"FROM events "
M module-db/Tables/EventsTable.hpp => module-db/Tables/EventsTable.hpp +7 -7
@@ 14,11 14,11 @@ struct EventsTableRow : public Record
{
std::string UID;
std::string title;
- TimePoint date_from = TIME_POINT_INVALID;
- TimePoint date_till = TIME_POINT_INVALID;
+ calendar::TimePoint date_from = TIME_POINT_INVALID;
+ calendar::TimePoint date_till = TIME_POINT_INVALID;
uint32_t reminder = 0;
uint32_t repeat = 0;
- TimePoint reminder_fired = TIME_POINT_INVALID;
+ calendar::TimePoint reminder_fired = TIME_POINT_INVALID;
std::string provider_type;
std::string provider_id;
std::string provider_iCalUid;
@@ 53,12 53,12 @@ class EventsTable : public Table<EventsTableRow, EventsTableFields>
bool drop();
EventsTableRow getByUID(const std::string &UID);
EventsTableRow getById(uint32_t id) override final;
- std::vector<EventsTableRow> selectByDatePeriod(TimePoint filter_from,
- TimePoint filter_till,
+ std::vector<EventsTableRow> selectByDatePeriod(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till,
uint32_t offset,
uint32_t limit);
uint32_t count() override final;
- uint32_t countFromFilter(TimePoint from, TimePoint till);
+ uint32_t countFromFilter(calendar::TimePoint from, calendar::TimePoint till);
uint32_t countByFieldId(const char *field, uint32_t id) override final;
std::vector<EventsTableRow> getLimitOffset(uint32_t offset, uint32_t limit) override final;
std::vector<EventsTableRow> getLimitOffsetByField(uint32_t offset,
@@ 67,7 67,7 @@ class EventsTable : public Table<EventsTableRow, EventsTableFields>
const char *str) override final;
std::vector<EventsTableRow> getLimitOffsetByDate(uint32_t offset, uint32_t limit);
- std::vector<EventsTableRow> SelectFirstUpcoming(TimePoint filter_from, TimePoint filter_till);
+ std::vector<EventsTableRow> SelectFirstUpcoming(calendar::TimePoint filter_from, calendar::TimePoint filter_till);
private:
const char *createTableQuery = "CREATE TABLE IF NOT EXISTS events("
M module-db/queries/calendar/QueryEventsGetFiltered.cpp => module-db/queries/calendar/QueryEventsGetFiltered.cpp +4 -1
@@ 5,7 5,10 @@
namespace db::query::events
{
- GetFiltered::GetFiltered(TimePoint filter_from, TimePoint filter_till, uint32_t offset, uint32_t limit)
+ GetFiltered::GetFiltered(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till,
+ uint32_t offset,
+ uint32_t limit)
: Query(Query::Type::Read), filter_from(filter_from), filter_till(filter_till), offset(offset), limit(limit)
{}
M module-db/queries/calendar/QueryEventsGetFiltered.hpp => module-db/queries/calendar/QueryEventsGetFiltered.hpp +6 -3
@@ 13,11 13,14 @@ namespace db::query::events
class GetFiltered : public Query
{
public:
- GetFiltered(TimePoint filter_from, TimePoint filter_till, uint32_t offset = 0, uint32_t limit = UINT32_MAX);
+ GetFiltered(calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till,
+ uint32_t offset = 0,
+ uint32_t limit = UINT32_MAX);
[[nodiscard]] auto debugInfo() const -> std::string override;
- TimePoint filter_from;
- TimePoint filter_till;
+ calendar::TimePoint filter_from;
+ calendar::TimePoint filter_till;
uint32_t offset;
uint32_t limit;
};
M module-db/queries/calendar/QueryEventsSelectFirstUpcoming.cpp => module-db/queries/calendar/QueryEventsSelectFirstUpcoming.cpp +1 -1
@@ 5,7 5,7 @@
namespace db::query::events
{
- SelectFirstUpcoming::SelectFirstUpcoming(TimePoint filter_from, TimePoint filter_till)
+ SelectFirstUpcoming::SelectFirstUpcoming(calendar::TimePoint filter_from, calendar::TimePoint filter_till)
: Query(Query::Type::Read), filter_from(filter_from), filter_till(filter_till)
{}
M module-db/queries/calendar/QueryEventsSelectFirstUpcoming.hpp => module-db/queries/calendar/QueryEventsSelectFirstUpcoming.hpp +3 -3
@@ 14,11 14,11 @@ namespace db::query::events
class SelectFirstUpcoming : public Query
{
public:
- SelectFirstUpcoming(TimePoint filter_from, TimePoint filter_till);
+ SelectFirstUpcoming(calendar::TimePoint filter_from, calendar::TimePoint filter_till);
[[nodiscard]] auto debugInfo() const -> std::string override;
- TimePoint filter_from;
- TimePoint filter_till;
+ calendar::TimePoint filter_from;
+ calendar::TimePoint filter_till;
};
/// Result of SelectFirstUpcoming query
M module-db/tests/AlarmsRecord_tests.cpp => module-db/tests/AlarmsRecord_tests.cpp +1 -1
@@ 184,7 184,7 @@ TEST_CASE("Alarms Record tests")
}
auto getQuery = [&](uint32_t id,
- TimePoint alarmTime,
+ calendar::TimePoint alarmTime,
uint32_t snooze,
AlarmStatus status,
uint32_t repeat,
M module-db/tests/AlarmsTable_tests.cpp => module-db/tests/AlarmsTable_tests.cpp +5 -5
@@ 139,11 139,11 @@ TEST_CASE("Alarms Table tests")
REQUIRE(alarmsTbl.add(
AlarmsTableRow(5, TimePointFromString("2020-12-11 07:15:00"), 1, AlarmStatus::On, 1, "file2.mp3")));
- const std::array<TimePoint, 5> paramTime{TimePointFromString("2020-12-11 07:15:00"),
- TimePointFromString("2020-11-11 15:10:00"),
- TimePointFromString("2020-11-11 15:15:00"),
- TimePointFromString("2020-11-12 17:10:00"),
- TimePointFromString("2020-11-11 19:25:00")};
+ const std::array<calendar::TimePoint, 5> paramTime{TimePointFromString("2020-12-11 07:15:00"),
+ TimePointFromString("2020-11-11 15:10:00"),
+ TimePointFromString("2020-11-11 15:15:00"),
+ TimePointFromString("2020-11-12 17:10:00"),
+ TimePointFromString("2020-11-11 19:25:00")};
REQUIRE(alarmsTbl.count() == 5);
auto entries = alarmsTbl.getLimitOffset(0, 5);
M module-db/tests/EventsRecord_tests.cpp => module-db/tests/EventsRecord_tests.cpp +8 -3
@@ 24,6 24,8 @@
#include <algorithm>
#include <iostream>
+using namespace std::chrono_literals;
+
static auto remove_events(EventsDB &db) -> bool
{
auto count = db.events.count();
@@ 728,7 730,7 @@ TEST_CASE("Events Record tests")
SECTION("Select first upcoming event")
{
- TimePoint start_date = TimePointFromString("2019-10-19 14:24:00");
+ calendar::TimePoint start_date = TimePointFromString("2019-10-19 14:24:00");
auto nextUpcoming = eventsRecordInterface.SelectFirstUpcoming(start_date, start_date);
REQUIRE(nextUpcoming.size() == 1);
EventsRecord nextEventsRecord = nextUpcoming.at(0);
@@ 797,7 799,9 @@ TEST_CASE("Events Record tests")
getAll(expectedRecords, numberOfEvents);
}
- auto getFiltered = [&](TimePoint filter_from, TimePoint filter_till, std::vector<EventsRecord> expected_records) {
+ auto getFiltered = [&](calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till,
+ std::vector<EventsRecord> expected_records) {
auto query = std::make_shared<db::query::events::GetFiltered>(filter_from, filter_till);
auto ret = eventsRecordInterface.runQuery(query);
auto result = dynamic_cast<db::query::events::GetFilteredResult *>(ret.get());
@@ 1009,7 1013,8 @@ TEST_CASE("Events Record tests")
EditQueryICS(testRecord6.UID, testRecord6);
}
- [[maybe_unused]] auto selectFirstUpcomingEvent = [&](TimePoint filter_from, TimePoint filter_till) {
+ [[maybe_unused]] auto selectFirstUpcomingEvent = [&](calendar::TimePoint filter_from,
+ calendar::TimePoint filter_till) {
auto query = std::make_shared<db::query::events::SelectFirstUpcoming>(filter_from, filter_till);
auto ret = eventsRecordInterface.runQuery(query);
auto result = dynamic_cast<db::query::events::SelectFirstUpcomingResult *>(ret.get());
M module-db/tests/EventsTable_tests.cpp => module-db/tests/EventsTable_tests.cpp +39 -37
@@ 15,6 15,8 @@
#include <purefs/filesystem_paths.hpp>
#include <unistd.h>
+using namespace std::chrono_literals;
+
static auto remove_events(EventsDB &db) -> bool
{
auto count = db.events.count();
@@ 164,8 166,8 @@ TEST_CASE("Events Table tests")
CHECK(eventsTbl.count() == 0);
uint32_t numberOfEvents = 7;
- TimePoint startDate = TimePointFromString("2019-10-20 14:30:00");
- TimePoint endDate = TimePointFromString("2019-10-20 15:30:00");
+ calendar::TimePoint startDate = TimePointFromString("2019-10-20 14:30:00");
+ calendar::TimePoint endDate = TimePointFromString("2019-10-20 15:30:00");
testRow1.date_from = startDate;
testRow1.date_till = endDate;
CHECK(eventsTbl.addDaily(testRow1));
@@ 199,8 201,8 @@ TEST_CASE("Events Table tests")
CHECK(eventsTbl.count() == 0);
uint32_t numberOfEvents = 4;
- TimePoint startDate = TimePointFromString("2019-10-20 14:30:00");
- TimePoint endDate = TimePointFromString("2019-10-20 15:30:00");
+ calendar::TimePoint startDate = TimePointFromString("2019-10-20 14:30:00");
+ calendar::TimePoint endDate = TimePointFromString("2019-10-20 15:30:00");
testRow1.date_from = startDate;
testRow1.date_till = endDate;
CHECK(eventsTbl.addWeekly(testRow1));
@@ 234,8 236,8 @@ TEST_CASE("Events Table tests")
CHECK(eventsTbl.count() == 0);
uint32_t numberOfEvents = 4;
- TimePoint startDate = TimePointFromString("2019-10-20 14:30:00");
- TimePoint endDate = TimePointFromString("2019-10-20 15:30:00");
+ calendar::TimePoint startDate = TimePointFromString("2019-10-20 14:30:00");
+ calendar::TimePoint endDate = TimePointFromString("2019-10-20 15:30:00");
testRow1.date_from = startDate;
testRow1.date_till = endDate;
CHECK(eventsTbl.addTwoWeeks(testRow1));
@@ 269,7 271,7 @@ TEST_CASE("Events Table tests")
CHECK(eventsTbl.count() == 0);
uint32_t numberOfEvents = 12;
- const std::array<TimePoint, 24> dates{
+ const std::array<calendar::TimePoint, 24> dates{
TimePointFromString("2019-01-20 14:30:00"), TimePointFromString("2019-01-20 15:30:00"),
TimePointFromString("2019-02-20 14:30:00"), TimePointFromString("2019-02-20 15:30:00"),
TimePointFromString("2019-03-20 14:30:00"), TimePointFromString("2019-03-20 15:30:00"),
@@ 316,14 318,14 @@ TEST_CASE("Events Table tests")
REQUIRE(eventsTbl.count() == 0);
uint32_t numberOfEvents = 4;
- std::array<TimePoint, 8> dates{TimePointFromString("2019-02-20 14:30:00"),
- TimePointFromString("2019-02-20 15:30:00"),
- TimePointFromString("2020-02-20 14:30:00"),
- TimePointFromString("2020-02-20 15:30:00"),
- TimePointFromString("2021-02-20 14:30:00"),
- TimePointFromString("2021-02-20 15:30:00"),
- TimePointFromString("2022-02-20 14:30:00"),
- TimePointFromString("2022-02-20 15:30:00")};
+ std::array<calendar::TimePoint, 8> dates{TimePointFromString("2019-02-20 14:30:00"),
+ TimePointFromString("2019-02-20 15:30:00"),
+ TimePointFromString("2020-02-20 14:30:00"),
+ TimePointFromString("2020-02-20 15:30:00"),
+ TimePointFromString("2021-02-20 14:30:00"),
+ TimePointFromString("2021-02-20 15:30:00"),
+ TimePointFromString("2022-02-20 14:30:00"),
+ TimePointFromString("2022-02-20 15:30:00")};
testRow1.date_from = dates[0];
testRow1.date_till = dates[1];
@@ 365,8 367,8 @@ TEST_CASE("Events Table tests")
{
auto check_custom_repeat = [&](uint32_t customRepeatOption,
uint32_t numberOfEvents,
- TimePoint originalStartDate,
- TimePoint originalEndDate) {
+ calendar::TimePoint originalStartDate,
+ calendar::TimePoint originalEndDate) {
if (eventsTbl.count() > 0) {
REQUIRE(remove_events(eventsDb));
}
@@ 394,8 396,8 @@ TEST_CASE("Events Table tests")
}
}
- TimePoint expectedStartDate = TimePointFromString("2020-12-07 14:30:00"); // monday
- TimePoint expectedEndDate = TimePointFromString("2020-12-07 15:30:00"); // monday
+ calendar::TimePoint expectedStartDate = TimePointFromString("2020-12-07 14:30:00"); // monday
+ calendar::TimePoint expectedEndDate = TimePointFromString("2020-12-07 15:30:00"); // monday
uint32_t i = 0;
for (uint32_t l = 0; l < numberOfWeeks; l++) {
@@ 437,8 439,8 @@ TEST_CASE("Events Table tests")
uint32_t customRepeatOption =
static_cast<uint32_t>(weekDayOption::monday) + static_cast<uint32_t>(weekDayOption::wednesday);
uint32_t numberOfEvents = 9;
- TimePoint originalStartDate = TimePointFromString("2020-12-10 14:30:00"); // thursday
- TimePoint originalEndDate = TimePointFromString("2020-12-10 15:30:00"); // thursday
+ calendar::TimePoint originalStartDate = TimePointFromString("2020-12-10 14:30:00"); // thursday
+ calendar::TimePoint originalEndDate = TimePointFromString("2020-12-10 15:30:00"); // thursday
check_custom_repeat(customRepeatOption, numberOfEvents, originalStartDate, originalEndDate);
}
@@ 449,8 451,8 @@ TEST_CASE("Events Table tests")
static_cast<uint32_t>(weekDayOption::monday) + static_cast<uint32_t>(weekDayOption::wednesday) +
static_cast<uint32_t>(weekDayOption::tuesday) + static_cast<uint32_t>(weekDayOption::sunday);
uint32_t numberOfEvents = 17;
- TimePoint originalStartDate = TimePointFromString("2020-12-10 14:30:00"); // thursday
- TimePoint originalEndDate = TimePointFromString("2020-12-10 15:30:00"); // thursday
+ calendar::TimePoint originalStartDate = TimePointFromString("2020-12-10 14:30:00"); // thursday
+ calendar::TimePoint originalEndDate = TimePointFromString("2020-12-10 15:30:00"); // thursday
check_custom_repeat(customRepeatOption, numberOfEvents, originalStartDate, originalEndDate);
}
@@ 459,8 461,8 @@ TEST_CASE("Events Table tests")
{
uint32_t customRepeatOption = static_cast<uint32_t>(weekDayOption::saturday);
uint32_t numberOfEvents = 5;
- TimePoint originalStartDate = TimePointFromString("2020-12-10 14:30:00"); // thursday
- TimePoint originalEndDate = TimePointFromString("2020-12-10 15:30:00"); // thursday
+ calendar::TimePoint originalStartDate = TimePointFromString("2020-12-10 14:30:00"); // thursday
+ calendar::TimePoint originalEndDate = TimePointFromString("2020-12-10 15:30:00"); // thursday
check_custom_repeat(customRepeatOption, numberOfEvents, originalStartDate, originalEndDate);
}
@@ 468,8 470,8 @@ TEST_CASE("Events Table tests")
SECTION("Check count from filter")
{
- TimePoint from = TimePointFromString("2019-10-20 14:30:00");
- TimePoint till = TimePointFromString("2019-10-24 14:20:00");
+ calendar::TimePoint from = TimePointFromString("2019-10-20 14:30:00");
+ calendar::TimePoint till = TimePointFromString("2019-10-24 14:20:00");
CHECK(eventsTbl.countFromFilter(from, till) == 4);
}
@@ 514,8 516,8 @@ TEST_CASE("Events Table tests")
CHECK(eventsTbl.count() == 6);
std::string newTitle = "Updated Title", newProviderID = "PurePhoneUpdated";
- TimePoint newDateFrom = TimePointFromString("2020-10-20 15:00:00"),
- newDateTill = TimePointFromString("2020-10-20 16:00:00");
+ calendar::TimePoint newDateFrom = TimePointFromString("2020-10-20 15:00:00"),
+ newDateTill = TimePointFromString("2020-10-20 16:00:00");
uint32_t newReminder = static_cast<uint32_t>(Reminder::one_week_before);
uint32_t newRepeatOption = static_cast<uint32_t>(Repeat::biweekly);
@@ 570,8 572,8 @@ TEST_CASE("Events Table tests")
std::string newTitle = "Updated Title", newProviderType = "PurePhoneUpdate", newProviderID = "newID",
newProvideriCalUid = "new iCalUid";
- TimePoint newDateFrom = TimePointFromString("2020-10-20 15:00:00"),
- newDateTill = TimePointFromString("2020-10-20 16:00:00");
+ calendar::TimePoint newDateFrom = TimePointFromString("2020-10-20 15:00:00"),
+ newDateTill = TimePointFromString("2020-10-20 16:00:00");
uint32_t newReminder = static_cast<uint32_t>(Reminder::one_week_before);
uint32_t newRepeatOption = static_cast<uint32_t>(Repeat::biweekly);
@@ 628,8 630,8 @@ TEST_CASE("Events Table tests")
std::string newTitle = "Updated Title", newProviderType = "PurePhoneUpdate", newProviderID = "newID",
newProvideriCalUid = "new iCalUid";
- TimePoint newDateFrom = TimePointFromString("2020-10-20 15:00:00"),
- newDateTill = TimePointFromString("2020-10-20 16:00:00");
+ calendar::TimePoint newDateFrom = TimePointFromString("2020-10-20 15:00:00"),
+ newDateTill = TimePointFromString("2020-10-20 16:00:00");
uint32_t newReminder = static_cast<uint32_t>(Reminder::one_week_before);
uint32_t newRepeatOption = static_cast<uint32_t>(Repeat::biweekly);
@@ 727,11 729,11 @@ TEST_CASE("Events Table tests")
}
CHECK(eventsTbl.count() == 0);
- TimePoint startDate1 = TimePointFromString("2018-10-20 14:24:00");
- TimePoint startDate2 = TimePointFromString("2020-10-20 14:24:00");
+ calendar::TimePoint startDate1 = TimePointFromString("2018-10-20 14:24:00");
+ calendar::TimePoint startDate2 = TimePointFromString("2020-10-20 14:24:00");
- TimePoint tillDate = TimePointFromString("2030-10-20 15:24:00");
- TimePoint firedDate = TimePointFromString("2018-10-20 14:24:00");
+ calendar::TimePoint tillDate = TimePointFromString("2030-10-20 15:24:00");
+ calendar::TimePoint firedDate = TimePointFromString("2018-10-20 14:24:00");
EventsTableRow testEvent1 = {{1},
.UID = "test1",
M module-db/tests/QueryInterface.cpp => module-db/tests/QueryInterface.cpp +2 -2
@@ 75,9 75,9 @@ TEST_CASE("Query interface")
auto msgJson = json11::Json::parse(testMessage, err);
REQUIRE(err.empty());
- Context context(msgJson);
+ parserFSM::Context context(msgJson);
auto listener = std::make_unique<db::EndpointListener>(
- [=](db::QueryResult *result, Context &context) {
+ [=](db::QueryResult *result, parserFSM::Context &context) {
if (auto SMSResult = dynamic_cast<db::query::SMSGetCountResult *>(result)) {
auto id = SMSResult->getResults();
auto body = json11::Json::object{{"count", static_cast<int>(id)}};
M module-gui/gui/dom/Item2JsonSerializingVisitor.cpp => module-gui/gui/dom/Item2JsonSerializingVisitor.cpp +1 -1
@@ 85,7 85,7 @@ void Item2JsonSerializingVisitor::visit(gui::BottomBar &item)
visit(static_cast<gui::Item &>(item));
}
-void Item2JsonSerializingVisitor::visit(gui::TopBar &item)
+void Item2JsonSerializingVisitor::visit(gui::top_bar::TopBar &item)
{
if (itemName.empty()) {
itemName = magic_enum::enum_name(visitor::Names::TopBar);
M module-gui/gui/dom/Item2JsonSerializingVisitor.hpp => module-gui/gui/dom/Item2JsonSerializingVisitor.hpp +1 -1
@@ 29,7 29,7 @@ namespace gui
void visit(gui::Window &item) override;
void visit(gui::Label &item) override;
void visit(gui::BottomBar &item) override;
- void visit(gui::TopBar &item) override;
+ void visit(gui::top_bar::TopBar &item) override;
public:
/// retrieves current state of the `sink`. The state of the `sink` after call is default-initialized
M module-gui/gui/widgets/BoxLayout.cpp => module-gui/gui/widgets/BoxLayout.cpp +6 -6
@@ 110,7 110,7 @@ namespace gui
/// this if back / front is crappy :|
if (previous) {
for (auto el = children.rbegin(); el != children.rend(); ++el) {
- if ((*el)->visible && (*el)->activeItem) {
+ if ((*el)->isActive()) {
setFocusItem(*el);
break;
}
@@ 118,7 118,7 @@ namespace gui
}
else {
for (auto &el : children) {
- if (el->visible && el->activeItem) {
+ if (el->isActive()) {
setFocusItem(el);
break;
}
@@ 375,7 375,7 @@ namespace gui
std::list<Item *>::iterator BoxLayout::nextNavigationItem(std::list<Item *>::iterator from)
{
return std::find_if(from, this->children.end(), [](auto &el) -> bool {
- if (el->visible && el->activeItem) {
+ if (el->isActive()) {
return true;
}
return false;
@@ 474,7 474,7 @@ namespace gui
bool success = false;
for (auto child : children) {
- if (child->activeItem && child->visible) {
+ if (child->isActive()) {
if (elementNumber == i) {
child->setFocus(true);
@@ 496,7 496,7 @@ namespace gui
auto last = true;
for (auto child = children.rbegin(); child != children.rend(); child++) {
- if ((*child)->activeItem && (*child)->visible && last) {
+ if ((*child)->isActive() && last) {
(*child)->setFocus(true);
focusItem = (*child);
last = false;
@@ 516,7 516,7 @@ namespace gui
if (child == focusItem) {
break;
}
- if (child->activeItem && child->visible) {
+ if (child->isActive()) {
index++;
}
}
M module-gui/gui/widgets/GridLayout.cpp => module-gui/gui/widgets/GridLayout.cpp +44 -47
@@ 22,25 22,34 @@ GridLayout::GridLayout(
auto it = this->getNavigationFocusedItem();
auto distance = std::distance(children.begin(), it);
+
switch (inputEvent.keyCode) {
case KeyCode::KEY_UP: {
- auto realRowSize = calculateRowSizeForBorderTransition(distance);
- this->setFocusItem((*std::next(it, (realRowSize - 1) * this->colSize)));
+ auto col = static_cast<uint32_t>(distance % colSize);
+ Item *item = getFirstActiveItem(getLastColumnIndex(col), (-1) * static_cast<int>(colSize));
+ if (item)
+ this->setFocusItem(item);
return true;
}
case KeyCode::KEY_DOWN: {
- auto realRowSize = calculateRowSizeForBorderTransition(distance);
- this->setFocusItem((*std::prev(it, (realRowSize - 1) * this->colSize)));
+ auto col = static_cast<uint32_t>(distance % colSize);
+ Item *item = getFirstActiveItem(col, static_cast<int>(colSize));
+ if (item)
+ this->setFocusItem(item);
return true;
}
case KeyCode::KEY_LEFT: {
- auto realColSize = calculateColumnSizeForBorderTransition(distance);
- this->setFocusItem((*std::next(it, realColSize - 1)));
+ auto row = static_cast<uint32_t>(distance / colSize);
+ Item *item = getFirstActiveItem(getLastRowIndex(row), -1);
+ if (item)
+ this->setFocusItem(item);
return true;
}
case KeyCode::KEY_RIGHT: {
- auto realColSize = calculateColumnSizeForBorderTransition(distance);
- this->setFocusItem((*std::prev(it, realColSize - 1)));
+ auto row = static_cast<uint32_t>(distance / colSize);
+ Item *item = getFirstActiveItem(colSize * row, 1);
+ if (item)
+ this->setFocusItem(item);
return true;
}
default: {
@@ 50,25 59,6 @@ GridLayout::GridLayout(
};
}
-uint32_t GridLayout::calculateColumnSizeForBorderTransition(const uint32_t currentPosition)
-{
- auto realColSize = colSize;
- if (elementsInIncompletedLastRow) {
- if (((currentPosition / colSize) + 1) >= rowSize)
- realColSize = elementsInIncompletedLastRow;
- }
- return realColSize;
-}
-uint32_t GridLayout::calculateRowSizeForBorderTransition(const uint32_t currentPosition)
-{
- auto realRowSize = rowSize;
- if (elementsInIncompletedLastRow) {
- if (((currentPosition % (colSize)) + 1) > elementsInIncompletedLastRow)
- realRowSize--;
- }
- return realRowSize;
-}
-
void GridLayout::handleItemsOutOfGridLayoutArea(uint32_t maxItemsInArea)
{
for (auto i = maxItemsInArea; i < children.size(); i++) {
@@ 88,16 78,6 @@ void GridLayout::resizeItems()
uint32_t el_in_x = area().w / grid.x;
uint32_t el_in_y = area().h / grid.y;
- elementsInIncompletedLastRow = 0;
- colSize = children.size() < area().w / grid.x ? children.size() : area().w / grid.x;
- rowSize = colSize != 0 ? (children.size() / colSize) : 1;
- if (colSize > 1 && (static_cast<double>(children.size()) / colSize) > 1.0) {
- elementsInIncompletedLastRow = children.size() % colSize;
- }
- if (elementsInIncompletedLastRow > 0) {
- rowSize++;
- }
-
uint32_t strech_x = 0;
uint32_t strech_y = 0;
uint32_t max_elements = el_in_x * el_in_y;
@@ 113,6 93,13 @@ void GridLayout::resizeItems()
handleItemsOutOfGridLayoutArea(max_elements);
return;
}
+
+ colSize = children.size() < area().w / grid.x ? children.size() : area().w / grid.x;
+ rowSize = colSize != 0 ? (children.size() / colSize) : 1;
+ if (colSize > 1 && (static_cast<double>(children.size()) / colSize) > 1.0 && (children.size() % colSize)) {
+ rowSize++;
+ }
+
if (el_in_x > 2)
strech_x = (area().w - grid.x * el_in_x) / (el_in_x - 1);
if (el_in_y > 2)
@@ 149,28 136,38 @@ void GridLayout::setNavigation()
for (auto it = children.begin(); it != children.end(); ++it, ++i) {
if (it != children.begin() && (i + 1) % colSize != 1) {
- (*it)->setNavigationItem(NavigationDirection::LEFT, nextNavigationItem(std::prev(it)));
+ (*it)->setNavigationItem(NavigationDirection::LEFT, getFirstActiveItem(i - 1, -1));
}
if (it != std::prev(children.end()) && (i + 1) % colSize != 0) {
- (*it)->setNavigationItem(NavigationDirection::RIGHT, nextNavigationItem(std::next(it)));
+ (*it)->setNavigationItem(NavigationDirection::RIGHT, getFirstActiveItem(i + 1, 1));
}
if ((i - offset) >= 0) {
- (*it)->setNavigationItem(NavigationDirection::UP, nextNavigationItem(std::prev(it, offset)));
+ (*it)->setNavigationItem(NavigationDirection::UP, getFirstActiveItem(i - offset, (-1) * offset));
}
if ((i + offset) < static_cast<int>(children.size())) {
- (*it)->setNavigationItem(NavigationDirection::DOWN, nextNavigationItem(std::next(it, offset)));
+ (*it)->setNavigationItem(NavigationDirection::DOWN, getFirstActiveItem(i + offset, offset));
}
}
}
-Item *GridLayout::nextNavigationItem(std::list<Item *>::iterator it)
+Item *GridLayout::getFirstActiveItem(uint32_t startposition, int step)
{
- if (it != this->children.end() && (*it)->visible && (*it)->activeItem) {
- return *it;
- }
- else {
- return nullptr;
+ Item *retItem = nullptr;
+ int index = static_cast<int>(startposition);
+ uint32_t row = startposition / colSize;
+ while (index >= 0 && index < static_cast<int>(children.size())) {
+ ///> condition for movement along row (+1,-1 step)
+ if ((step == 1 || step == -1) && (index / colSize != row)) {
+ break;
+ }
+ std::list<Item *>::iterator tmpit = std::next(children.begin(), index);
+ if ((*tmpit)->isActive()) {
+ retItem = *tmpit;
+ break;
+ }
+ index += step;
}
+ return retItem;
}
M module-gui/gui/widgets/GridLayout.hpp => module-gui/gui/widgets/GridLayout.hpp +15 -9
@@ 26,23 26,29 @@ namespace gui
{}
GridLayout() : GridLayout(0, 0, 0, 0, {0, 0})
{}
- /// when reached top -> start from bottom. When reached left, start from right.
- bool navigationRotate = true;
void resizeItems() override;
void setNavigation() override;
- Item *nextNavigationItem(std::list<Item *>::iterator it);
uint32_t rowSize = 0;
uint32_t colSize = 0;
- ///> elementsInIncompletedLastRow describes how many items has been put to last row,
- /// in case when items for last row is not equal to colSize
- uint32_t elementsInIncompletedLastRow = 0;
private:
- uint32_t calculateColumnSizeForBorderTransition(const uint32_t currentPosition);
- uint32_t calculateRowSizeForBorderTransition(const uint32_t currentPosition);
-
void handleItemsOutOfGridLayoutArea(uint32_t maxItemsInArea);
+ Item *getFirstActiveItem(uint32_t startposition, int step);
+ inline uint32_t getLastColumnIndex(uint32_t col)
+ {
+ auto lastcolumnindex = col;
+ while ((lastcolumnindex + colSize) < children.size())
+ lastcolumnindex += colSize;
+ return lastcolumnindex;
+ }
+ inline uint32_t getLastRowIndex(uint32_t row)
+ {
+ uint32_t lastrowindex = colSize * row + (colSize - 1);
+ while (lastrowindex >= children.size())
+ lastrowindex--;
+ return lastrowindex;
+ }
};
}; // namespace gui
M module-gui/gui/widgets/Item.hpp => module-gui/gui/widgets/Item.hpp +5 -0
@@ 344,6 344,11 @@ namespace gui
/// remove timer from item and as a result - destory it
void detachTimer(Timer &timer);
+ /// simple check function to determine if item is active && visible
+ inline bool isActive()
+ {
+ return (activeItem && visible);
+ }
virtual void accept(GuiVisitor &visitor);
protected:
M module-gui/gui/widgets/ProgressBar.cpp => module-gui/gui/widgets/ProgressBar.cpp +8 -6
@@ 35,14 35,15 @@ namespace gui
}
}
- void ProgressBar::setValue(unsigned int value) noexcept
+ bool ProgressBar::setValue(unsigned int value) noexcept
{
currentValue = std::clamp(value, 0U, maxValue);
+ return currentValue == value;
}
- void ProgressBar::update(int value) noexcept
+ bool ProgressBar::update(int value) noexcept
{
- setValue(currentValue + value);
+ return setValue(currentValue + value);
}
void ProgressBar::setPercentageValue(unsigned int value) noexcept
@@ 110,14 111,15 @@ namespace gui
}
}
- void CircularProgressBar::setValue(unsigned int value) noexcept
+ bool CircularProgressBar::setValue(unsigned int value) noexcept
{
currentValue = std::clamp(value, 0U, maxValue);
+ return value == currentValue;
}
- void CircularProgressBar::update(int value) noexcept
+ bool CircularProgressBar::update(int value) noexcept
{
- setValue(currentValue + value);
+ return setValue(currentValue + value);
}
void CircularProgressBar::setPercentageValue(unsigned int value) noexcept
M module-gui/gui/widgets/ProgressBar.hpp => module-gui/gui/widgets/ProgressBar.hpp +6 -6
@@ 17,8 17,8 @@ namespace gui
virtual ~Progress() noexcept = default;
virtual void setMaximum(unsigned int value) = 0;
- virtual void setValue(unsigned int value) = 0;
- virtual void update(int value = 1) = 0;
+ virtual auto setValue(unsigned int value) -> bool = 0;
+ virtual auto update(int value = 1) -> bool = 0;
virtual void setPercentageValue(unsigned int value) = 0;
};
@@ 28,8 28,8 @@ namespace gui
ProgressBar(Item *parent, std::uint32_t x, std::uint32_t y, std::uint32_t w, std::uint32_t h);
void setMaximum(unsigned int value) noexcept override;
- void setValue(unsigned int value) noexcept override;
- void update(int value = 1) noexcept override;
+ auto setValue(unsigned int value) noexcept -> bool override;
+ auto update(int value = 1) noexcept -> bool override;
void setPercentageValue(unsigned int value) noexcept override;
void buildDrawListImplementation(std::list<Command> &commands) override;
@@ 49,8 49,8 @@ namespace gui
CircularProgressBar(Item *parent, const Circle::ShapeParams &shape);
void setMaximum(unsigned int value) noexcept override;
- void setValue(unsigned int value) noexcept override;
- void update(int value = 1) noexcept override;
+ auto setValue(unsigned int value) noexcept -> bool override;
+ auto update(int value = 1) noexcept -> bool override;
void setPercentageValue(unsigned int value) noexcept override;
void buildDrawListImplementation(std::list<Command> &commands) override;
M module-gui/gui/widgets/Style.hpp => module-gui/gui/widgets/Style.hpp +1 -0
@@ 138,6 138,7 @@ namespace style
inline constexpr auto set = "common_set";
inline constexpr auto yes = "common_yes";
inline constexpr auto no = "common_no";
+ inline constexpr auto check = "common_check";
inline constexpr auto Switch = "common_switch";
inline constexpr auto options = "common_options";
inline constexpr auto information = "common_information";
M module-gui/gui/widgets/TopBar.cpp => module-gui/gui/widgets/TopBar.cpp +90 -46
@@ 11,7 11,7 @@
#include "common_data/EventStore.hpp"
-namespace gui
+namespace gui::top_bar
{
namespace networkTechnology
{
@@ 20,14 20,47 @@ namespace gui
constexpr uint32_t w = 130;
constexpr uint32_t h = 20;
} // namespace networkTechnology
- const uint32_t TopBar::signalOffset = 35;
- const uint32_t TopBar::batteryOffset = 413;
- gui::TopBar::TimeMode TopBar::timeMode = TimeMode::TIME_24H;
+
+ static constexpr uint32_t signalOffset = 35;
+ static constexpr uint32_t batteryOffset = 413;
+
+ TopBar::TimeMode TopBar::timeMode = TimeMode::TIME_24H;
uint32_t TopBar::time = 0;
- TopBar::TopBar(Item *parent, uint32_t x, uint32_t y, uint32_t w, uint32_t h) : Rect{parent, x, y, w, h}
+ void Configuration::enable(Indicator indicator)
+ {
+ set(indicator, true);
+ }
+
+ void Configuration::enable(const Indicators &indicators)
+ {
+ for (auto indicator : indicators) {
+ enable(indicator);
+ }
+ }
+
+ void Configuration::disable(Indicator indicator)
{
+ set(indicator, false);
+ }
+
+ void Configuration::set(Indicator indicator, bool enabled)
+ {
+ indicatorStatuses[indicator] = enabled;
+ }
+
+ auto Configuration::isEnabled(Indicator indicator) const -> bool
+ {
+ return indicatorStatuses.at(indicator);
+ }
+
+ auto Configuration::getIndicatorsConfiguration() const noexcept -> const IndicatorStatuses &
+ {
+ return indicatorStatuses;
+ }
+ TopBar::TopBar(Item *parent, uint32_t x, uint32_t y, uint32_t w, uint32_t h) : Rect{parent, x, y, w, h}
+ {
prepareWidget();
setFillColor(ColorFullWhite);
@@ 48,7 81,7 @@ namespace gui
val = batteryBars.size();
}
for (unsigned int i = 0; i < batteryBars.size(); ++i) {
- if (elements.battery) {
+ if (configuration.isEnabled(Indicator::Battery)) {
batteryBars[i]->setVisible(i == val);
}
else {
@@ 59,7 92,6 @@ namespace gui
void TopBar::prepareWidget()
{
-
signal[0] = new gui::Image(this, signalOffset, 17, 0, 0, "signal0");
signal[1] = new gui::Image(this, signalOffset, 17, 0, 0, "signal1");
signal[2] = new gui::Image(this, signalOffset, 17, 0, 0, "signal2");
@@ 111,48 143,56 @@ namespace gui
updateNetworkAccessTechnology();
}
- void TopBar::setActive(std::list<std::pair<TopBar::Elements, bool>> elements)
+ auto TopBar::getConfiguration() const noexcept -> const Configuration &
+ {
+ return configuration;
+ }
+
+ void TopBar::configure(Configuration &&config)
{
- for (auto el : elements) {
- setActive(el.first, el.second);
+ if (config.isEnabled(Indicator::Lock)) {
+ // In current implementation, lock and time indicators are mutually exclusive.
+ // I.e. enabling the lock indicator disables the time indicator.
+ config.disable(Indicator::Time);
+ }
+
+ for (auto [indicator, enabled] : config.getIndicatorsConfiguration()) {
+ setIndicatorStatus(indicator, enabled);
}
+ configuration = std::move(config);
}
- void TopBar::setActive(TopBar::Elements element, bool active)
+ void TopBar::setIndicatorStatus(Indicator indicator, bool enabled)
{
- switch (element) {
- case Elements::BATTERY: {
- elements.battery = active;
- showBattery(elements.battery);
- } break;
- case Elements::LOCK: {
- elements.lock = active;
- lock->setVisible(active);
- if (active)
- timeLabel->setVisible(false);
- } break;
- case Elements::SIGNAL: {
- elements.signal = active;
+ switch (indicator) {
+ case Indicator::Signal:
updateSignalStrength();
- } break;
- case Elements::TIME: {
- elements.time = active;
- timeLabel->setVisible(active);
- if (active)
+ break;
+ case Indicator::Time:
+ timeLabel->setVisible(enabled);
+ if (enabled) {
lock->setVisible(false);
- } break;
- case Elements::SIM:
- elements.sim = active;
+ }
+ break;
+ case Indicator::Lock:
+ lock->setVisible(enabled);
+ if (enabled) {
+ timeLabel->setVisible(false);
+ }
+ break;
+ case Indicator::Battery:
+ showBattery(enabled);
+ break;
+ case Indicator::SimCard:
simSet();
break;
- case Elements::NETWORK_ACCESS_TECHNOLOGY:
- elements.networkAccessTechnology = active;
+ case Indicator::NetworkAccessTechnology:
updateNetworkAccessTechnology();
break;
- };
+ }
}
- uint32_t calculateBatteryBars(uint32_t percentage)
+ uint32_t TopBar::calculateBatteryBars(uint32_t percentage)
{
uint32_t level = 0;
if (percentage <= 5) // level critical
@@ 177,13 217,13 @@ namespace gui
bool TopBar::updateBattery(uint32_t percent)
{
- showBattery(elements.battery);
+ showBattery(configuration.isEnabled(Indicator::Battery));
return true;
}
bool TopBar::updateBattery(bool plugged)
{
- showBattery(elements.battery);
+ showBattery(configuration.isEnabled(Indicator::Battery));
return true;
}
@@ 216,7 256,7 @@ namespace gui
for (uint32_t i = 0; i < signalImgCount; i++) {
signal[i]->setVisible(false);
}
- if (elements.signal) {
+ if (configuration.isEnabled(Indicator::Signal)) {
auto rssiBar = Store::GSM::get()->getSignalStrength().rssiBar;
if (rssiBar < Store::RssiBar::noOfSupprtedBars) {
signal[static_cast<size_t>(rssiBar)]->setVisible(true);
@@ 229,7 269,7 @@ namespace gui
bool TopBar::updateNetworkAccessTechnology()
{
- if (elements.networkAccessTechnology) {
+ if (configuration.isEnabled(Indicator::NetworkAccessTechnology)) {
auto accessTechnology = Store::GSM::get()->getNetwork().accessTechnology;
constexpr auto text2g = "2G";
@@ 258,16 298,16 @@ namespace gui
return true;
}
- void TopBar::setTime(const UTF8 &time)
+ void TopBar::setTime(const UTF8 &value)
{
- timeLabel->setText(time);
+ timeLabel->setText(value);
}
- void TopBar::setTime(const uint32_t &time, bool mode24H)
+ void TopBar::setTime(uint32_t value, bool mode24H)
{
setTime(utils::time::Time());
timeMode = (mode24H ? TimeMode::TIME_24H : TimeMode::TIME_12H);
- this->time = time;
+ time = value;
}
UTF8 TopBar::getTimeString()
@@ 276,13 316,17 @@ namespace gui
return timeLabel->getText();
}
+ uint32_t TopBar::getTime() const noexcept
+ {
+ return time;
+ }
void TopBar::simSet()
{
- if (!sim) {
+ if (sim == nullptr) {
return;
}
- else if (elements.sim) {
+ if (configuration.isEnabled(Indicator::SimCard)) {
return sim->show(Store::GSM::get()->sim);
}
sim->visible = false;
M module-gui/gui/widgets/TopBar.hpp => module-gui/gui/widgets/TopBar.hpp +61 -41
@@ 1,21 1,52 @@
-// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
-#ifndef MODULE_GUI_GUI_WIDGETS_TOPBAR_HPP_
-#define MODULE_GUI_GUI_WIDGETS_TOPBAR_HPP_
+#pragma once
#include "Image.hpp"
#include "Label.hpp"
#include "Rect.hpp"
#include "TopBar/SIM.hpp"
#include <common_data/EventStore.hpp>
+
+#include <vector>
#include <map>
-namespace gui
+namespace gui::top_bar
{
+ enum class Indicator
+ {
+ Signal,
+ Time,
+ Lock,
+ Battery,
+ SimCard,
+ NetworkAccessTechnology
+ };
+ using Indicators = std::vector<Indicator>;
+ using IndicatorStatuses = std::map<Indicator, bool>;
- static const uint32_t batteryBarsCount = 6;
- static const uint32_t signalImgCount = 6;
+ /**
+ * Carries the top bar configuration.
+ */
+ class Configuration
+ {
+ public:
+ void enable(Indicator indicator);
+ void enable(const Indicators &indicators);
+ void disable(Indicator indicator);
+ void set(Indicator indicator, bool enabled);
+ [[nodiscard]] auto isEnabled(Indicator indicator) const -> bool;
+ [[nodiscard]] auto getIndicatorsConfiguration() const noexcept -> const IndicatorStatuses &;
+
+ private:
+ IndicatorStatuses indicatorStatuses = {{Indicator::Signal, false},
+ {Indicator::Time, false},
+ {Indicator::Lock, false},
+ {Indicator::Battery, false},
+ {Indicator::SimCard, false},
+ {Indicator::NetworkAccessTechnology, false}};
+ };
/// Header of most of design Windows
///
@@ 31,19 62,10 @@ namespace gui
/// [signal] [title ] [sim] [battery]
class TopBar : public Rect
{
- static const uint32_t signalOffset;
- static const uint32_t batteryOffset;
+ static constexpr uint32_t batteryBarsCount = 6;
+ static constexpr uint32_t signalImgCount = 6;
public:
- enum class Elements
- {
- SIGNAL = 0x01,
- LOCK,
- BATTERY,
- TIME,
- SIM,
- NETWORK_ACCESS_TECHNOLOGY
- };
enum class TimeMode
{
TIME_12H,
@@ 60,32 82,32 @@ namespace gui
std::map<const Store::Battery::State, Image *> batteryChargings = {
{Store::Battery::State::Charging, nullptr}, {Store::Battery::State::PluggedNotCharging, nullptr}};
gui::SIM *sim = nullptr;
- void prepareWidget();
+ Configuration configuration;
static TimeMode timeMode;
+ void prepareWidget();
+
/// show bars in number - 0 bars, 1 bar, 2 bars...
void batteryShowBars(uint32_t val);
- /// elements shown on TopBar
- struct
- {
- bool signal : 1;
- bool lock : 1;
- bool battery : 1;
- bool time : 1;
- bool sim : 1;
- bool networkAccessTechnology : 1;
- } elements = {false, false, false, false, true, true};
+ static uint32_t calculateBatteryBars(uint32_t percentage);
+
+ /**
+ * Sets the status of the top bar indicator.
+ * @param indicator Indicator
+ */
+ void setIndicatorStatus(Indicator indicator, bool enabled);
public:
TopBar(Item *parent, uint32_t x, uint32_t y, uint32_t w, uint32_t h);
/**
- * @brief Hides or shows images.
- * @note LOCK and TIME are located in the same place so only 1 can be active at the same time.
+ * Configures the top bar.
+ * @param configuration Top bar configuration
*/
- void setActive(TopBar::Elements element, bool active);
- void setActive(std::list<std::pair<TopBar::Elements, bool>> elements);
+ void configure(Configuration &&config);
+ [[nodiscard]] auto getConfiguration() const noexcept -> const Configuration &;
+
/**
* @brief Sets charge level of the battery based on percent value. This will cause appropriate image to be
* displayed.
@@ 103,16 125,14 @@ namespace gui
bool updateNetworkAccessTechnology();
void simSet();
- void setTime(const UTF8 &time);
- void setTime(const uint32_t &time, bool mode24H);
+
+ void setTime(const UTF8 &value);
+ void setTime(uint32_t value, bool mode24H);
+
UTF8 getTimeString();
- uint32_t getTime()
- {
- return time;
- };
+ uint32_t getTime() const noexcept;
+
void accept(GuiVisitor &visitor) override;
};
-} /* namespace gui */
-
-#endif /* MODULE_GUI_GUI_WIDGETS_TOPBAR_HPP_ */
+} // namespace gui::top_bar
M module-gui/gui/widgets/visitor/GuiVisitor.hpp => module-gui/gui/widgets/visitor/GuiVisitor.hpp +5 -2
@@ 11,7 11,10 @@ namespace gui
class Window;
class Label;
class BottomBar;
- class TopBar;
+ namespace top_bar
+ {
+ class TopBar;
+ }
/// The general purpose abstract interface for enabling Double-Dispatch behavior throughout `gui::Item`'s
/// inheritance hierarchy.
@@ 24,7 27,7 @@ namespace gui
virtual void visit(gui::Window &item) = 0;
virtual void visit(gui::Label &item) = 0;
virtual void visit(gui::BottomBar &item) = 0;
- virtual void visit(gui::TopBar &item) = 0;
+ virtual void visit(gui::top_bar::TopBar &item) = 0;
virtual ~GuiVisitor() = default;
};
} // namespace gui
M module-gui/test/test-google/test-gui-gridlayout.cpp => module-gui/test/test-google/test-gui-gridlayout.cpp +150 -2
@@ 67,7 67,20 @@ class GridLayoutTesting : public ::testing::Test
Box->addWidget(item);
}
}
-
+ void addItem(gui::BoxLayout *Box,
+ uint32_t item_w,
+ uint32_t item_h,
+ uint32_t id,
+ bool active = true,
+ const gui::Margins &margins = gui::Margins())
+ {
+ auto item = new TestItem(nullptr, 0, 0, item_w, item_h);
+ item->ID = id;
+ item->visible = true;
+ item->setMargins(margins);
+ item->activeItem = active;
+ Box->addWidget(item);
+ }
gui::GridLayout *gridLayout = nullptr;
///> GridLayout test constants
@@ 120,6 133,139 @@ TEST_F(GridLayoutTesting, Navigate_Test)
ASSERT_EQ(1 + expColSize, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
<< "element with ID " << 1 + expColSize << " should have focus";
}
+
+TEST_F(GridLayoutTesting, Navigate_Test_ActiveItems_1)
+{
+ ///> Test for grid layout with 48 elements (A - active item, N - non active item, NV - non visible item)
+ ///> | 1 A | 2 NA | 3 A | 4 NA | 5 A | 6 NA | 7 A | 8 NA | 9 A | 10 NA | 11 A | 12 NA |
+ ///> | 13 NA | 14 A | 15 NA | 16 A | 17 NA | 18 A | 19 NA | 20 A | 21 NA | 22 A | 23 NA | 24 A |
+ ///> | 25 A | 26 NA | 27 A | 28 NA | 29 A | 30 NA | 31 A | 32 NA | 33 A | 34 NA | 35 A | 36 NA |
+ ///> | 37 NA | 38 A | 39 NA | 40 A | 41 NA | 42 A | 43 NA | 44 A | 45 NA | 46 A | 47 NA | 48 A |
+ ///> | 49 NV | 50 NV | 51 NV | 52 NV |
+ for (uint32_t i = 1; i <= 12; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, (i % 2) ? true : false);
+ }
+ for (uint32_t i = 13; i <= 24; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, ((i + 1) % 2) ? true : false);
+ }
+ for (uint32_t i = 25; i <= 36; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, (i % 2) ? true : false);
+ }
+ for (uint32_t i = 37; i <= 48; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, ((i + 1) % 2) ? true : false);
+ }
+ ///> Add some items to exceed grid layout area
+ for (uint32_t i = 49; i <= 52; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, true);
+ }
+ gridLayout->setFocus(true);
+ ASSERT_EQ(gridLayout->rowSize, 4) << "row size is not " << 4 << " as expected";
+ ASSERT_EQ(gridLayout->colSize, 12) << "col size is not " << 12 << " as expected";
+ ASSERT_EQ(52, gridLayout->children.size()) << "GridLayout should contain " << 52 << " elements";
+
+ ASSERT_EQ(1, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 1 << " should have focus";
+ moveNTimes(gridLayout, 2, gui::KeyCode::KEY_RIGHT);
+ ASSERT_EQ(5, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 5 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_DOWN);
+ ASSERT_EQ(5 + (2 * expColSize), dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 5 + (2 * expColSize) << " should have focus";
+ moveNTimes(gridLayout, 2, gui::KeyCode::KEY_LEFT);
+ ASSERT_EQ(1 + (2 * expColSize), dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 1 + (2 * expColSize) << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_DOWN);
+ ASSERT_EQ(1, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 1 << " should have focus";
+}
+
+TEST_F(GridLayoutTesting, Navigate_Test_ActiveItems_2_BorderCallback)
+{
+ ///> Test for grid layout with 48 elements
+ ///> | 1 A | 2 NA | 3 A | 4 NA | 5 A | 6 NA | 7 A | 8 NA | 9 A | 10 NA | 11 A | 12 NA |
+ ///> | 13 NA | 14 A | 15 NA | 16 A | 17 NA | 18 A | 19 NA | 20 A | 21 NA | 22 A | 23 NA | 24 A |
+ ///> | 25 A | 26 NA | 27 A | 28 NA | 29 A | 30 NA | 31 A | 32 NA | 33 A | 34 NA | 35 A | 36 NA |
+ ///> | 37 NA | 38 A | 39 NA |
+ for (uint32_t i = 1; i <= 12; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, (i % 2) ? true : false);
+ }
+ for (uint32_t i = 13; i <= 24; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, ((i + 1) % 2) ? true : false);
+ }
+ for (uint32_t i = 25; i <= 36; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, (i % 2) ? true : false);
+ }
+ for (uint32_t i = 37; i <= 39; i++) {
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, i, ((i + 1) % 2) ? true : false);
+ }
+
+ gridLayout->setFocus(true);
+ ASSERT_EQ(gridLayout->rowSize, 4) << "row size is not " << 4 << " as expected";
+ ASSERT_EQ(gridLayout->colSize, 12) << "col size is not " << 12 << " as expected";
+ ASSERT_EQ(39, gridLayout->children.size()) << "GridLayout should contain " << 39 << " elements";
+
+ ASSERT_EQ(1, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 1 << " should have focus";
+ moveNTimes(gridLayout, 2, gui::KeyCode::KEY_LEFT);
+ ASSERT_EQ(9, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 9 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_UP);
+ ASSERT_EQ(33, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 33 << " should have focus";
+ moveNTimes(gridLayout, 3, gui::KeyCode::KEY_LEFT);
+ ASSERT_EQ(27, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 27 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_DOWN);
+ ASSERT_EQ(3, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 3 << " should have focus";
+ moveNTimes(gridLayout, 5, gui::KeyCode::KEY_RIGHT);
+ ASSERT_EQ(1, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 1 << " should have focus";
+
+ ///> Test for grid layout with 1 element
+ ///> | 1NA |
+ gridLayout->erase();
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, 1, false);
+ ASSERT_EQ(gridLayout->children.size(), 1) << "elements size is not " << 1 << " as expected";
+ ASSERT_EQ(gridLayout->rowSize, 1) << "row size is not " << 1 << " as expected";
+ ASSERT_EQ(gridLayout->colSize, 1) << "col size is not " << 1 << " as expected";
+ gridLayout->setFocus(false);
+ gridLayout->setFocus(true);
+ ASSERT_EQ(nullptr, gridLayout->getFocusItem()) << "no element shall be focused";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_LEFT);
+ ASSERT_EQ(nullptr, gridLayout->getFocusItem()) << "no element shall be focused";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_RIGHT);
+ ASSERT_EQ(nullptr, gridLayout->getFocusItem()) << "no element shall be focused";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_UP);
+ ASSERT_EQ(nullptr, gridLayout->getFocusItem()) << "no element shall be focused";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_DOWN);
+ ASSERT_EQ(nullptr, gridLayout->getFocusItem()) << "no element shall be focused";
+ ///> Test for grid layout with 1 element
+ ///> | 1NA | 1A |
+ gridLayout->erase();
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, 1, false);
+ addItem(gridLayout, testStyle::grid_item_w, testStyle::grid_item_h, 2, true);
+ ASSERT_EQ(gridLayout->children.size(), 2) << "elements size is not " << 2 << " as expected";
+ ASSERT_EQ(gridLayout->rowSize, 1) << "row size is not " << 1 << " as expected";
+ ASSERT_EQ(gridLayout->colSize, 2) << "col size is not " << 2 << " as expected";
+ gridLayout->setFocus(false);
+ gridLayout->setFocus(true);
+ ASSERT_EQ(2, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 2 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_LEFT);
+ ASSERT_EQ(2, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 2 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_RIGHT);
+ ASSERT_EQ(2, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 2 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_UP);
+ ASSERT_EQ(2, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 2 << " should have focus";
+ moveNTimes(gridLayout, 1, gui::KeyCode::KEY_DOWN);
+ ASSERT_EQ(2, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
+ << "element with ID " << 2 << " should have focus";
+}
+
///> TODO: Enable this test when issue with setFocus will be resolved
TEST_F(GridLayoutTesting, DISABLED_Border_Callback_Test)
{
@@ 149,7 295,7 @@ TEST_F(GridLayoutTesting, DISABLED_Border_Callback_Test)
<< "element with ID " << 37 << " should have focus";
moveNTimes(gridLayout, 1, gui::KeyCode::KEY_LEFT);
ASSERT_EQ(46, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
- << "element with ID " << 37 << " should have focus";
+ << "element with ID " << 46 << " should have focus";
moveNTimes(gridLayout, 1, gui::KeyCode::KEY_DOWN);
ASSERT_EQ(10, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
<< "element with ID " << 10 << " should have focus";
@@ 170,6 316,7 @@ TEST_F(GridLayoutTesting, DISABLED_Border_Callback_Test)
ASSERT_EQ(gridLayout->children.size(), 1) << "elements size is not " << 1 << " as expected";
ASSERT_EQ(gridLayout->rowSize, 1) << "row size is not " << 1 << " as expected";
ASSERT_EQ(gridLayout->colSize, 1) << "col size is not " << 1 << " as expected";
+
gridLayout->setFocus(true);
ASSERT_EQ(1, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
@@ 194,6 341,7 @@ TEST_F(GridLayoutTesting, DISABLED_Border_Callback_Test)
ASSERT_EQ(gridLayout->children.size(), 2) << "elements size is not " << 2 << " as expected";
ASSERT_EQ(gridLayout->rowSize, 1) << "row size is not " << 1 << " as expected";
ASSERT_EQ(gridLayout->colSize, 2) << "col size is not " << 2 << " as expected";
+
gridLayout->setFocus(true);
ASSERT_EQ(1, dynamic_cast<TestItem *>(gridLayout->getFocusItem())->ID)
M module-gui/test/test-google/test-gui-visitor-call.cpp => module-gui/test/test-google/test-gui-visitor-call.cpp +1 -1
@@ 25,7 25,7 @@ class VisitorMock : public gui::GuiVisitor
MOCK_METHOD1(visit, void(gui::Window &item));
MOCK_METHOD1(visit, void(gui::Label &item));
MOCK_METHOD1(visit, void(gui::BottomBar &item));
- MOCK_METHOD1(visit, void(gui::TopBar &item));
+ MOCK_METHOD1(visit, void(gui::top_bar::TopBar &item));
};
class CustomRect : public gui::Rect
M module-services/service-appmgr/model/ApplicationManager.cpp => module-services/service-appmgr/model/ApplicationManager.cpp +16 -8
@@ 106,12 106,6 @@ namespace app::manager
{
registerMessageHandlers();
blockingTimer->connect([this](sys::Timer &) { onPhoneLocked(); });
- settings->registerValueChange(settings::SystemProperties::displayLanguage,
- [this](std::string value) { displayLanguageChanged(value); });
- settings->registerValueChange(settings::SystemProperties::inputLanguage,
- [this](std::string value) { inputLanguageChanged(value); });
- settings->registerValueChange(settings::SystemProperties::lockTime,
- [this](std::string value) { lockTimeChanged(value); });
}
sys::ReturnCodes ApplicationManager::InitHandler()
@@ 120,6 114,18 @@ namespace app::manager
utils::localize.setFallbackLanguage(utils::localize.DefaultLanguage);
utils::localize.setDisplayLanguage(displayLanguage);
utils::localize.setInputLanguage(inputLanguage);
+ settings->registerValueChange(
+ settings::SystemProperties::displayLanguage,
+ [this](std::string value) { displayLanguageChanged(value); },
+ settings::SettingsScope::Global);
+ settings->registerValueChange(
+ settings::SystemProperties::inputLanguage,
+ [this](std::string value) { inputLanguageChanged(value); },
+ settings::SettingsScope::Global);
+ settings->registerValueChange(
+ settings::SystemProperties::lockTime,
+ [this](std::string value) { lockTimeChanged(value); },
+ settings::SettingsScope::Global);
startSystemServices();
startBackgroundApplications();
@@ 161,6 167,7 @@ namespace app::manager
sys::ReturnCodes ApplicationManager::DeinitHandler()
{
+ settings->unregisterValueChange();
closeApplications();
closeServices();
return sys::ReturnCodes::Success;
@@ 540,7 547,8 @@ namespace app::manager
return false;
}
displayLanguage = requestedLanguage;
- settings->setValue(settings::SystemProperties::displayLanguage, displayLanguage);
+ settings->setValue(
+ settings::SystemProperties::displayLanguage, displayLanguage, settings::SettingsScope::Global);
utils::localize.setDisplayLanguage(displayLanguage);
rebuildActiveApplications();
return true;
@@ 555,7 563,7 @@ namespace app::manager
return false;
}
inputLanguage = requestedLanguage;
- settings->setValue(settings::SystemProperties::inputLanguage, inputLanguage);
+ settings->setValue(settings::SystemProperties::inputLanguage, inputLanguage, settings::SettingsScope::Global);
utils::localize.setInputLanguage(inputLanguage);
return true;
}
M module-services/service-cellular/CellularRequestHandler.cpp => module-services/service-cellular/CellularRequestHandler.cpp +2 -0
@@ 22,6 22,8 @@
#include <module-cellular/at/response.hpp>
+using namespace cellular;
+
void CellularRequestHandler::handle(ImeiRequest &request, at::Result &result)
{
if (!request.checkModemResponse(result)) {
M module-services/service-cellular/CellularUrcHandler.cpp => module-services/service-cellular/CellularUrcHandler.cpp +2 -0
@@ 11,6 11,8 @@
#include <service-evtmgr/Constants.hpp>
#include <service-appmgr/Controller.hpp>
+using namespace at::urc;
+
// this static function will be replaced by Settings API
static bool isSettingsAutomaticTimeSyncEnabled()
{
M module-services/service-cellular/CellularUrcHandler.hpp => module-services/service-cellular/CellularUrcHandler.hpp +11 -13
@@ 18,27 18,25 @@
#include <module-cellular/at/UrcResponse.hpp>
#include <module-cellular/at/UrcQiurc.hpp>
-using namespace at::urc;
-
/**
* ServiceCellular helper for handling Urc messages
*/
-class CellularUrcHandler : public UrcHandler
+class CellularUrcHandler : public at::urc::UrcHandler
{
public:
CellularUrcHandler(ServiceCellular &cellularService) : cellularService(cellularService)
{}
- void Handle(Clip &urc) final;
- void Handle(Creg &urc) final;
- void Handle(Cmti &urc) final;
- void Handle(Cusd &urc) final;
- void Handle(Ctze &urc) final;
- void Handle(Qind &urc) final;
- void Handle(Cpin &urc) final;
- void Handle(Qiurc &urc) final;
- void Handle(PoweredDown &urc) final;
- void Handle(UrcResponse &urc) final;
+ void Handle(at::urc::Clip &urc) final;
+ void Handle(at::urc::Creg &urc) final;
+ void Handle(at::urc::Cmti &urc) final;
+ void Handle(at::urc::Cusd &urc) final;
+ void Handle(at::urc::Ctze &urc) final;
+ void Handle(at::urc::Qind &urc) final;
+ void Handle(at::urc::Cpin &urc) final;
+ void Handle(at::urc::Qiurc &urc) final;
+ void Handle(at::urc::PoweredDown &urc) final;
+ void Handle(at::urc::UrcResponse &urc) final;
/**
* Gets the response that should be returned after handling Urc
M module-services/service-cellular/ServiceCellular.cpp => module-services/service-cellular/ServiceCellular.cpp +10 -8
@@ 204,8 204,6 @@ ServiceCellular::ServiceCellular() : sys::Service(serviceName, "", cellularStack
sys::Bus::SendMulticast(msg.value(), sys::BusChannels::ServiceCellularNotifications, this);
};
registerMessageHandlers();
- settings->registerValueChange(settings::Cellular::volte_on,
- [this](const std::string &value) { volteChanged(value); });
packetData = std::make_unique<packet_data::PacketData>(*this);
packetData->loadAPNSettings();
}
@@ 235,6 233,8 @@ sys::ReturnCodes ServiceCellular::InitHandler()
board = EventManagerServiceAPI::GetBoard(this);
state.set(this, State::ST::WaitForStartPermission);
+ settings->registerValueChange(settings::Cellular::volte_on,
+ [this](const std::string &value) { volteChanged(value); });
return sys::ReturnCodes::Success;
}
@@ 297,12 297,12 @@ void ServiceCellular::registerMessageHandlers()
return handleCellularGetActiveContextsMessage(msg);
});
- connect(typeid(CellularGetAPNMessage), [&](sys::Message *request) -> sys::MessagePointer {
- connect(typeid(CellularGetCurrentOperatorMessage), [&](sys::Message *request) -> sys::MessagePointer {
- auto msg = static_cast<CellularGetCurrentOperatorMessage *>(request);
- return handleCellularGetCurrentOperator(msg);
- });
+ connect(typeid(CellularGetCurrentOperatorMessage), [&](sys::Message *request) -> sys::MessagePointer {
+ auto msg = static_cast<CellularGetCurrentOperatorMessage *>(request);
+ return handleCellularGetCurrentOperator(msg);
+ });
+ connect(typeid(CellularGetAPNMessage), [&](sys::Message *request) -> sys::MessagePointer {
auto msg = static_cast<CellularGetAPNMessage *>(request);
return handleCellularGetAPNMessage(msg);
});
@@ 1284,7 1284,9 @@ bool ServiceCellular::handleSimState(at::SimState state, const std::string messa
switch (state) {
case at::SimState::Ready:
Store::GSM::get()->sim = Store::GSM::get()->selected;
- settings->setValue(settings::SystemProperties::activeSim, utils::enumToString(Store::GSM::get()->selected));
+ settings->setValue(settings::SystemProperties::activeSim,
+ utils::enumToString(Store::GSM::get()->selected),
+ settings::SettingsScope::Global);
// SIM causes SIM INIT, only on ready
response =
std::move(std::make_unique<CellularNotificationMessage>(CellularNotificationMessage::Type::SIM_READY));
M module-services/service-cellular/service-cellular/CellularRequestHandler.hpp => module-services/service-cellular/service-cellular/CellularRequestHandler.hpp +8 -10
@@ 6,21 6,19 @@
#include "RequestHandler.hpp"
#include "service-cellular/ServiceCellular.hpp"
-using namespace cellular;
-
-class CellularRequestHandler : public RequestHandler
+class CellularRequestHandler : public cellular::RequestHandler
{
public:
CellularRequestHandler(ServiceCellular &serviceCellular) : cellular(serviceCellular)
{}
- void handle(ImeiRequest &request, at::Result &result) final;
- void handle(UssdRequest &request, at::Result &result) final;
- void handle(CallRequest &request, at::Result &result) final;
- void handle(PasswordRegistrationRequest &request, at::Result &result) final;
- void handle(SupplementaryServicesRequest &request, at::Result &result) final;
- void handle(PinChangeRequest &request, at::Result &result) final;
- void handle(ClirRequest &request, at::Result &result) final;
+ void handle(cellular::ImeiRequest &request, at::Result &result) final;
+ void handle(cellular::UssdRequest &request, at::Result &result) final;
+ void handle(cellular::CallRequest &request, at::Result &result) final;
+ void handle(cellular::PasswordRegistrationRequest &request, at::Result &result) final;
+ void handle(cellular::SupplementaryServicesRequest &request, at::Result &result) final;
+ void handle(cellular::PinChangeRequest &request, at::Result &result) final;
+ void handle(cellular::ClirRequest &request, at::Result &result) final;
private:
ServiceCellular &cellular;
M module-services/service-cellular/service-cellular/PacketDataTypes.hpp => module-services/service-cellular/service-cellular/PacketDataTypes.hpp +64 -2
@@ 5,6 5,10 @@
#include <string>
#include <memory>
+#include <unordered_map>
+#include <map>
+
+#include <Utils.hpp>
namespace packet_data
{
@@ 22,10 26,11 @@ namespace packet_data
*/
enum class APNType
{
- Default, ///< for data traffic
+ Default, ///< only one APN is set as default
IMS, ///< IP Multimedia Subsystem for eg VoLTE
MMS, ///< for MMS service
- Fota ///< for Firmware Update
+ Fota, ///< for Firmware Update
+ Internet //< for data traffic
};
/**
@@ 81,6 86,63 @@ namespace packet_data
std::string password;
std::string ip; /// set after connection
+ std::string getAuthMethod()
+ {
+ return utils::enumToString(authMethod);
+ }
+
+ void setAuthMethod(const std::string &str)
+ {
+ if (str == "NONE")
+ authMethod = AuthMethod::NONE;
+ else if (str == "AUTO")
+ authMethod = AuthMethod::AUTO;
+ else if (str == "CHAP")
+ authMethod = AuthMethod::CHAP;
+ else if (str == "PAP")
+ authMethod = AuthMethod::PAP;
+ else
+ authMethod = AuthMethod::NONE;
+ }
+
+ std::string getApnType()
+ {
+ return utils::enumToString(apnType);
+ }
+
+ void setApnType(const std::string &str)
+ {
+ if (str == "Default")
+ apnType = APNType::Default;
+ else if (str == "Fota")
+ apnType = APNType::Fota;
+ else if (str == "IMS")
+ apnType = APNType::IMS;
+ else if (str == "Internet")
+ apnType = APNType::Internet;
+ else if (str == "MMS")
+ apnType = APNType::MMS;
+ else
+ apnType = APNType::Internet;
+ }
+
+ std::string getApnProtocol()
+ {
+ return utils::enumToString(contextType);
+ }
+
+ void setApnProtocol(const std::string &str)
+ {
+ if (str == "ipv4")
+ contextType = ContextType::ipv4;
+ else if (str == "ipv6")
+ contextType = ContextType::ipv6;
+ else if (str == "ipv4v6")
+ contextType = ContextType::ipv4v6;
+ else
+ contextType = ContextType::ipv4;
+ }
+
bool isEmpty() const noexcept
{
return apn.empty();
M module-services/service-db/DBServiceAPI.cpp => module-services/service-db/DBServiceAPI.cpp +48 -12
@@ 60,7 60,10 @@ auto DBServiceAPI::ThreadGetCount(sys::Service *serv, EntryState state) -> uint3
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto threadResponse = dynamic_cast<DBThreadResponseMessage *>(ret.second.get());
- assert(threadResponse != nullptr);
+ if (threadResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return 0;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (threadResponse->retCode == 1)) {
return threadResponse->count;
}
@@ 91,7 94,10 @@ auto DBServiceAPI::ContactGetByIDCommon(sys::Service *serv, std::shared_ptr<DBCo
{
auto ret = sys::Bus::SendUnicast(contactMsg, service::name::db, serv, DefaultTimeoutInMs);
auto contactResponse = dynamic_cast<DBContactResponseMessage *>(ret.second.get());
- assert(contactResponse != nullptr);
+ if (contactResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return nullptr;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (contactResponse->retCode != 0)) {
return std::move(contactResponse->records);
}
@@ 133,7 139,10 @@ auto DBServiceAPI::MatchContactByPhoneNumber(sys::Service *serv, const utils::Ph
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto contactResponse = dynamic_cast<DBContactNumberResponseMessage *>(ret.second.get());
- assert(contactResponse);
+ if (contactResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return nullptr;
+ }
return std::move(contactResponse->contact);
}
@@ 180,7 189,10 @@ auto DBServiceAPI::ContactAdd(sys::Service *serv, const ContactRecord &rec) -> b
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto contactResponse = dynamic_cast<DBContactResponseMessage *>(ret.second.get());
- assert(contactResponse != nullptr);
+ if (contactResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return false;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (contactResponse->retCode != 0)) {
return true;
}
@@ 194,7 206,10 @@ auto DBServiceAPI::ContactRemove(sys::Service *serv, uint32_t id) -> bool
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto contactResponse = dynamic_cast<DBContactResponseMessage *>(ret.second.get());
- assert(contactResponse != nullptr);
+ if (contactResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return false;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (contactResponse->retCode != 0)) {
return true;
}
@@ 207,7 222,10 @@ auto DBServiceAPI::ContactUpdate(sys::Service *serv, const ContactRecord &rec) -
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto contactResponse = dynamic_cast<DBContactResponseMessage *>(ret.second.get());
- assert(contactResponse != nullptr);
+ if (contactResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return false;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (contactResponse->retCode != 0)) {
return true;
}
@@ 225,7 243,10 @@ auto DBServiceAPI::ContactSearch(sys::Service *serv, UTF8 primaryName, UTF8 alte
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto contactResponse = dynamic_cast<DBContactResponseMessage *>(ret.second.get());
- assert(contactResponse != nullptr);
+ if (contactResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return nullptr;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (contactResponse->retCode != 0)) {
return std::move(contactResponse->records);
}
@@ 240,7 261,10 @@ auto DBServiceAPI::CalllogAdd(sys::Service *serv, const CalllogRecord &rec) -> C
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto calllogResponse = dynamic_cast<DBCalllogResponseMessage *>(ret.second.get());
- assert(calllogResponse != nullptr);
+ if (calllogResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return CalllogRecord();
+ }
if ((ret.first == sys::ReturnCodes::Success) && (calllogResponse->retCode != 0)) {
auto records = *calllogResponse->records;
if (!records.empty()) {
@@ 258,7 282,10 @@ auto DBServiceAPI::CalllogRemove(sys::Service *serv, uint32_t id) -> bool
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto calllogResponse = dynamic_cast<DBCalllogResponseMessage *>(ret.second.get());
- assert(calllogResponse != nullptr);
+ if (calllogResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return false;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (calllogResponse->retCode != 0)) {
return true;
}
@@ 273,7 300,10 @@ auto DBServiceAPI::CalllogUpdate(sys::Service *serv, const CalllogRecord &rec) -
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto calllogResponse = dynamic_cast<DBCalllogResponseMessage *>(ret.second.get());
- assert(calllogResponse != nullptr);
+ if (calllogResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return false;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (calllogResponse->retCode != 0)) {
return true;
}
@@ 286,7 316,10 @@ auto DBServiceAPI::CalllogGetCount(sys::Service *serv, EntryState state) -> uint
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto calllogResponse = dynamic_cast<DBCalllogResponseMessage *>(ret.second.get());
- assert(calllogResponse != nullptr);
+ if (calllogResponse == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return 0;
+ }
if ((ret.first == sys::ReturnCodes::Success) && (calllogResponse->retCode != 0)) {
return calllogResponse->count;
}
@@ 310,7 343,10 @@ auto DBServiceAPI::GetCountryCodeByMCC(sys::Service *serv, uint32_t mcc) -> uint
auto ret = sys::Bus::SendUnicast(msg, service::name::db, serv, DefaultTimeoutInMs);
auto response = dynamic_cast<DBCountryCodeResponseMessage *>(ret.second.get());
- assert(response != nullptr);
+ if (response == nullptr) {
+ LOG_ERROR("DB response error, return code: %s", c_str(ret.first));
+ return 0;
+ }
if (ret.first == sys::ReturnCodes::Success) {
return (response->row.country_code);
}
M module-services/service-db/agents/settings/Settings.cpp => module-services/service-db/agents/settings/Settings.cpp +46 -23
@@ 52,9 52,9 @@ namespace settings
{
LOG_DEBUG("handleVariableChanged");
if (auto msg = dynamic_cast<settings::Messages::VariableChanged *>(req)) {
- auto key = msg->getPath().variable;
+ auto key = msg->getPath();
auto val = msg->getValue();
- LOG_DEBUG("handleVariableChanged: (k=v): (%s=%s)", key.c_str(), val.value_or("").c_str());
+ LOG_DEBUG("handleVariableChanged: (k=v): (%s=%s)", key.to_string().c_str(), val.value_or("").c_str());
ValueCb::iterator it_cb = cbValues.find(key);
if (cbValues.end() != it_cb) {
auto [cb, cbWithName] = it_cb->second;
@@ 62,13 62,13 @@ namespace settings
// in case of two callbacks there is a need to duplicate the value
auto value = std::move(val.value_or(""));
cb(std::string{value});
- cbWithName(key, std::move(value));
+ cbWithName(key.variable, std::move(value));
}
else if (nullptr != cb) {
cb(std::move(val.value_or("")));
}
else {
- cbWithName(key, std::move(val.value_or("")));
+ cbWithName(key.variable, std::move(val.value_or("")));
}
}
}
@@ 115,56 115,79 @@ namespace settings
return std::make_shared<sys::ResponseMessage>();
}
- void Settings::registerValueChange(const std::string &variableName, ValueChangedCallback cb)
+ void Settings::registerValueChange(const std::string &variableName, ValueChangedCallback cb, SettingsScope scope)
{
- ValueCb::iterator it_cb = cbValues.find(variableName);
- if (cbValues.end() != it_cb && nullptr != it_cb->second.first) {
- LOG_INFO("Callback function on value change (%s) already exists, rewriting", variableName.c_str());
- }
- cbValues[variableName].first = cb;
EntryPath path;
path.variable = variableName;
path.service = app->GetName();
+ path.scope = scope;
+
+ auto it_cb = cbValues.find(path);
+ if (cbValues.end() != it_cb && nullptr != it_cb->second.first) {
+ LOG_INFO("Callback function on value change (%s) already exists, rewriting", path.to_string().c_str());
+ }
+ cbValues[path].first = cb;
+
auto msg = std::make_shared<settings::Messages::RegisterOnVariableChange>(path);
sendMsg(std::move(msg));
}
- void Settings::registerValueChange(const std::string &variableName, ValueChangedCallbackWithName cb)
+ void Settings::registerValueChange(const std::string &variableName,
+ ValueChangedCallbackWithName cb,
+ SettingsScope scope)
{
- auto it_cb = cbValues.find(variableName);
- if (cbValues.end() != it_cb && nullptr != it_cb->second.second) {
- LOG_INFO("Callback function on value change (%s) already exists, rewriting", variableName.c_str());
- }
- cbValues[variableName].second = cb;
EntryPath path;
path.variable = variableName;
path.service = app->GetName();
+ path.scope = scope;
+
+ auto it_cb = cbValues.find(path);
+ if (cbValues.end() != it_cb && nullptr != it_cb->second.second) {
+ LOG_INFO("Callback function on value change (%s) already exists, rewriting", path.to_string().c_str());
+ }
+ cbValues[path].second = cb;
+
auto msg = std::make_shared<settings::Messages::RegisterOnVariableChange>(path);
sendMsg(std::move(msg));
}
- void Settings::unregisterValueChange(const std::string &variableName)
+ void Settings::unregisterValueChange(const std::string &variableName, SettingsScope scope)
{
- ValueCb::iterator it_cb = cbValues.find(variableName);
+ EntryPath path;
+ path.variable = variableName;
+ path.service = app->GetName();
+ path.scope = scope;
+
+ auto it_cb = cbValues.find(path);
if (cbValues.end() == it_cb) {
- LOG_INFO("Callback function on value change (%s) does not exist", variableName.c_str());
+ LOG_INFO("Callback function on value change (%s) does not exist", path.to_string().c_str());
}
else {
+ LOG_DEBUG("[Settings::unregisterValueChange] %s", path.to_string().c_str());
cbValues.erase(it_cb);
}
- EntryPath path;
- path.variable = variableName;
- path.service = app->GetName();
auto msg = std::make_shared<settings::Messages::UnregisterOnVariableChange>(path);
sendMsg(std::move(msg));
}
- void Settings::setValue(const std::string &variableName, const std::string &variableValue)
+ void Settings::unregisterValueChange()
+ {
+ for (auto it_cb : cbValues) {
+ LOG_DEBUG("[Settings::unregisterValueChange] %s", it_cb.first.to_string().c_str());
+ auto msg = std::make_shared<settings::Messages::UnregisterOnVariableChange>(it_cb.first);
+ sendMsg(std::move(msg));
+ }
+ cbValues.clear();
+ LOG_INFO("Unregistered all settings variable change on application (%s)", app->GetName().c_str());
+ }
+
+ void Settings::setValue(const std::string &variableName, const std::string &variableValue, SettingsScope scope)
{
EntryPath path;
path.variable = variableName;
path.service = app->GetName();
+ path.scope = scope;
auto msg = std::make_shared<settings::Messages::SetVariable>(path, variableValue);
sendMsg(std::move(msg));
}
M module-services/service-db/agents/settings/SettingsAgent.cpp => module-services/service-db/agents/settings/SettingsAgent.cpp +20 -26
@@ 4,8 4,6 @@
#include "SettingsAgent.hpp"
#include "Settings_queries.hpp"
-#include <service-db/SettingsMessages.hpp>
-
#include <Database/Database.hpp>
#include <Service/Service.hpp>
#include <module-sys/Service/Bus.hpp>
@@ 24,16 22,6 @@ SettingsAgent::SettingsAgent(sys::Service *parentService) : DatabaseAgent(parent
void SettingsAgent::initDb()
{
- auto notifications = database->query(settings::Statements::getAllNotifications);
- if (nullptr == notifications || 0 == notifications->getRowCount()) {
- return;
- }
- do {
- variableChangeRecipents[(*notifications)[0].getString()].insert((*notifications)[1].getString());
- /*what about mode/profile
- modeChangeRecipents;
- profileChangeRecipents;*/
- } while (notifications->nextRow());
}
void SettingsAgent::deinitDb()
@@ 95,8 83,7 @@ auto SettingsAgent::getAgentName() -> const std::string
// dbSingleVar
auto SettingsAgent::dbGetValue(settings::EntryPath path) -> std::optional<std::string>
{
- // auto retQuery = database->query(settings::Statements::getValue, path.to_string());
- auto retQuery = database->query(settings::Statements::getValue, path.variable.c_str());
+ auto retQuery = database->query(settings::Statements::getValue, path.to_string().c_str());
if (nullptr == retQuery || 1 != retQuery->getRowCount()) {
return std::string{};
}
@@ 106,17 93,18 @@ auto SettingsAgent::dbGetValue(settings::EntryPath path) -> std::optional<std::s
auto SettingsAgent::dbSetValue(settings::EntryPath path, std::string value) -> bool
{
/// insert or update
- return database->execute(settings::Statements::insertValue, path.variable.c_str(), value.c_str());
+ return database->execute(settings::Statements::insertValue, path.to_string().c_str(), value.c_str());
}
auto SettingsAgent::dbRegisterValueChange(settings::EntryPath path) -> bool
{
- return database->execute(settings::Statements::setNotification, path.variable.c_str(), path.service.c_str());
+ return database->execute(settings::Statements::setNotification, path.to_string().c_str(), path.service.c_str());
}
auto SettingsAgent::dbUnregisterValueChange(settings::EntryPath path) -> bool
{
- return database->execute(settings::Statements::clearNotificationdRow, path.variable.c_str());
+ return database->execute(
+ settings::Statements::clearNotificationdRow, path.to_string().c_str(), path.service.c_str());
}
// db Profile
@@ 223,12 211,13 @@ auto SettingsAgent::handleSetVariable(sys::Message *req) -> sys::MessagePointer
auto oldValue = dbGetValue(path);
if (oldValue.has_value() && oldValue.value() != value) {
dbSetValue(path, value);
- // for (auto service : variableChangeRecipents[path.to_string()]) {
- for (auto service : variableChangeRecipents[path.variable]) {
- if (service != path.service) {
+ LOG_DEBUG("[SettingsAgent::handleSetVariable] %s=%s", path.to_string().c_str(), value.c_str());
+ for (auto regPath : variableChangeRecipents[path.to_string()]) {
+ if (regPath.service != path.service) {
auto updateMsg =
- std::make_shared<settings::Messages::VariableChanged>(path, value, oldValue.value_or(""));
- sys::Bus::SendUnicast(std::move(updateMsg), service, parentService);
+ std::make_shared<settings::Messages::VariableChanged>(regPath, value, oldValue.value_or(""));
+ sys::Bus::SendUnicast(std::move(updateMsg), regPath.service, parentService);
+ LOG_DEBUG("[SettingsAgent::handleSetVariable] notified service: %s", regPath.service.c_str());
}
}
}
@@ 242,14 231,18 @@ auto SettingsAgent::handleRegisterOnVariableChange(sys::Message *req) -> sys::Me
auto path = msg->getPath();
if (dbRegisterValueChange(path)) {
auto it = variableChangeRecipents.find(path.to_string());
- if (variableChangeRecipents.end() == it || it->second.end() == it->second.find(path.service)) {
- variableChangeRecipents[path.to_string()] = {path.service};
+ if (variableChangeRecipents.end() == it || it->second.end() == it->second.find(path)) {
+ variableChangeRecipents[path.to_string()] = {path};
auto currentValue = dbGetValue(path).value_or("");
auto msgValue = std::make_shared<::settings::Messages::VariableChanged>(path, currentValue, "");
sys::Bus::SendUnicast(std::move(msgValue), msg->sender, parentService);
+ LOG_DEBUG("[SettingsAgent::handleRegisterOnVariableChange] %s=%s to %s",
+ path.to_string().c_str(),
+ currentValue.c_str(),
+ msg->sender.c_str());
}
else {
- it->second.insert(path.service);
+ it->second.insert(path);
}
}
}
@@ 263,7 256,8 @@ auto SettingsAgent::handleUnregisterOnVariableChange(sys::Message *req) -> sys::
if (dbUnregisterValueChange(path)) {
auto it = variableChangeRecipents.find(path.to_string());
if (variableChangeRecipents.end() != it) {
- it->second.erase(path.service);
+ it->second.erase(path);
+ LOG_DEBUG("[SettingsAgent::handleUnregisterOnVariableChange] %s", path.to_string().c_str());
}
}
}
M module-services/service-db/agents/settings/SettingsAgent.hpp => module-services/service-db/agents/settings/SettingsAgent.hpp +2 -1
@@ 32,7 32,8 @@ class SettingsAgent : public DatabaseAgent
auto getAgentName() -> const std::string override;
private:
- using MapOfRecipentsToBeNotified = std::map<std::string, std::set<std::string>>;
+ // using MapOfRecipentsToBeNotified = std::map<std::string, std::set<std::string>>;
+ using MapOfRecipentsToBeNotified = std::map<std::string, std::set<settings::EntryPath>>;
MapOfRecipentsToBeNotified variableChangeRecipents;
using SetOfRecipents = std::set<std::string>;
SetOfRecipents profileChangedRecipents;
M module-services/service-db/agents/settings/SystemSettings.hpp => module-services/service-db/agents/settings/SystemSettings.hpp +7 -0
@@ 24,6 24,13 @@ namespace settings
constexpr inline auto bondedDevices = "bt_bonded_devices";
constexpr inline auto btKeys = "bt_keys";
} // namespace Bluetooth
+ namespace Brightness
+ {
+ constexpr inline auto state = "br_state";
+ constexpr inline auto brightnessLevel = "br_level";
+ constexpr inline auto gammaFactor = "br_gamma_Factor";
+ constexpr inline auto autoMode = "br_auto_mode";
+ } // namespace Brightness
namespace Cellular
{
M module-services/service-db/service-db/Settings.hpp => module-services/service-db/service-db/Settings.hpp +15 -10
@@ 5,6 5,8 @@
#include <module-sys/Service/Message.hpp>
#include <service-db/DBServiceName.hpp>
+#include "SettingsScope.hpp"
+#include "SettingsMessages.hpp"
#include <cstdint>
#include <functional>
@@ 16,11 18,6 @@
namespace settings
{
- namespace Messages
- {
- class SettingsMessage;
- }
-
class Settings
{
public:
@@ 36,10 33,18 @@ namespace settings
Settings(sys::Service *app, const std::string &dbAgentName = service::name::db);
virtual ~Settings();
- void setValue(const std::string &variableName, const std::string &variableValue);
- void registerValueChange(const std::string &variableName, ValueChangedCallback cb);
- void registerValueChange(const std::string &variableName, ValueChangedCallbackWithName cb);
- void unregisterValueChange(const std::string &variableName);
+ void setValue(const std::string &variableName,
+ const std::string &variableValue,
+ SettingsScope scope = SettingsScope::AppLocal);
+ void registerValueChange(const std::string &variableName,
+ ValueChangedCallback cb,
+ SettingsScope scope = SettingsScope::AppLocal);
+ void registerValueChange(const std::string &variableName,
+ ValueChangedCallbackWithName cb,
+ SettingsScope scope = SettingsScope::AppLocal);
+ void unregisterValueChange(const std::string &variableName, SettingsScope scope = SettingsScope::AppLocal);
+ /// unregisters all registered variables (both global and local)
+ void unregisterValueChange();
void getAllProfiles(OnAllProfilesRetrievedCallback cb);
void setCurrentProfile(const std::string &profile);
@@ 61,7 66,7 @@ namespace settings
std::string phoneMode;
std::string profile;
- using ValueCb = std::map<std::string, std::pair<ValueChangedCallback, ValueChangedCallbackWithName>>;
+ using ValueCb = std::map<EntryPath, std::pair<ValueChangedCallback, ValueChangedCallbackWithName>>;
ValueCb cbValues;
ModeChangedCallback cbMode;
OnAllModesRetrievedCallback cbAllModes;
M module-services/service-db/service-db/SettingsMessages.hpp => module-services/service-db/service-db/SettingsMessages.hpp +30 -0
@@ 5,6 5,7 @@
#include <MessageType.hpp>
#include <Service/Message.hpp>
+#include <service-db/SettingsScope.hpp>
#include <list>
#include <memory>
@@ 20,11 21,40 @@ namespace settings
std::string service;
std::string profile;
std::string variable;
+ SettingsScope scope;
[[nodiscard]] auto to_string(std::string sep = "\\") const -> std::string
{
+ if (SettingsScope::Global == scope) {
+ return variable;
+ }
return mode + sep + service + sep + profile + sep + variable;
}
+
+ bool operator<(const EntryPath &other) const
+ {
+ if (mode < other.mode)
+ return true;
+ if (mode > other.mode)
+ return false;
+ if (service < other.service)
+ return true;
+ if (service > other.service)
+ return false;
+ if (profile < other.profile)
+ return true;
+ if (profile > other.profile)
+ return false;
+ if (variable < other.variable)
+ return true;
+ if (variable > other.variable)
+ return false;
+ if (scope < other.scope)
+ return true;
+ if (scope > other.scope)
+ return false;
+ return false;
+ }
};
namespace Messages
A module-services/service-db/service-db/SettingsScope.hpp => module-services/service-db/service-db/SettingsScope.hpp +12 -0
@@ 0,0 1,12 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+namespace settings
+{
+ enum class SettingsScope
+ {
+ Global,
+ AppLocal
+ };
+}
M module-services/service-db/test/test-service-db-settings-messages.cpp => module-services/service-db/test/test-service-db-settings-messages.cpp +4 -4
@@ 118,13 118,13 @@ TEST_CASE("Settings Messages")
settings::Service settings("settings");
settings.InitHandler();
- sys::Bus::SendUnicast(std::make_shared<settings::Messages::RegisterOnVariableChange>(
- settings::EntryPath({"mode", "service", "profile", "variable"})),
+ sys::Bus::SendUnicast(std::make_shared<settings::Messages::RegisterOnVariableChange>(settings::EntryPath(
+ {"mode", "service", "profile", "variable", settings::SettingsScope::AppLocal})),
"db-worker",
&settings);
- sys::Bus::SendUnicast(std::make_shared<settings::Messages::UnregisterOnVariableChange>(
- settings::EntryPath({"mode", "service", "profile", "variable"})),
+ sys::Bus::SendUnicast(std::make_shared<settings::Messages::UnregisterOnVariableChange>(settings::EntryPath(
+ {"mode", "service", "profile", "variable", settings::SettingsScope::AppLocal})),
"db-worker",
&settings);
}
M module-services/service-db/test/test-service-db-settings-testservices.hpp => module-services/service-db/test/test-service-db-settings-testservices.hpp +6 -4
@@ 28,26 28,28 @@ namespace settings
if (auto msg = dynamic_cast<settings::UTMsg::ReqRegValChg *>(req)) {
debug("ReqRegValChg", msg->name, msg->value);
whoRequestedNotifyOnChange = msg->sender;
- mySettings->registerValueChange(msg->name, ([this](std::string value) {
+ mySettings->registerValueChange(msg->name,
+ ([this](std::string value) {
ValueChanged(value);
auto cnf = std::make_shared<settings::UTMsg::CnfValChg>("", value);
sys::Bus::SendUnicast(
std::move(cnf), whoRequestedNotifyOnChange, this);
- }));
+ }),
+ settings::SettingsScope::Global);
auto cnf = std::make_shared<settings::UTMsg::CnfRegValChg>(msg->name, msg->value);
sys::Bus::SendUnicast(std::move(cnf), whoRequestedNotifyOnChange, this);
}
else if (auto msg = dynamic_cast<settings::UTMsg::ReqUnRegValChg *>(req)) {
// unregister
debug("ReqUnRegValChg", msg->name, msg->value);
- mySettings->unregisterValueChange(msg->name);
+ mySettings->unregisterValueChange(msg->name, settings::SettingsScope::Global);
auto cnf = std::make_shared<settings::UTMsg::CnfUnRegValChg>(msg->name, msg->value);
sys::Bus::SendUnicast(std::move(cnf), msg->sender, this);
}
else if (auto msg = dynamic_cast<settings::UTMsg::ReqSetVal *>(req)) {
// set value
debug("ReqSetVal", msg->name, msg->value);
- mySettings->setValue(msg->name, msg->value);
+ mySettings->setValue(msg->name, msg->value, settings::SettingsScope::Global);
auto cnf = std::make_shared<settings::UTMsg::CnfReqSetVal>(msg->name, msg->value);
sys::Bus::SendUnicast(std::move(cnf), msg->sender, this);
}
M module-services/service-desktop/DesktopMessages.cpp => module-services/service-desktop/DesktopMessages.cpp +1 -0
@@ 6,6 6,7 @@
namespace sdesktop::developerMode
{
+ using namespace parserFSM;
void Event::send()
{
MessageHandler::putToSendQueue(context.createSimpleResponse());
M module-services/service-desktop/ServiceDesktop.cpp => module-services/service-desktop/ServiceDesktop.cpp +4 -3
@@ 29,8 29,6 @@ ServiceDesktop::ServiceDesktop() : sys::Service(service::name::service_desktop,
updateOS = std::make_unique<UpdateMuditaOS>(this);
settings = std::make_unique<settings::Settings>(this);
- settings->registerValueChange(updateos::settings::history,
- [this](const std::string &value) { updateOS->setInitialHistory(value); });
}
ServiceDesktop::~ServiceDesktop()
@@ 42,7 40,7 @@ sys::ReturnCodes ServiceDesktop::InitHandler()
{
desktopWorker = std::make_unique<WorkerDesktop>(this);
const bool ret = desktopWorker->init(
- {{sdesktop::RECEIVE_QUEUE_BUFFER_NAME, sizeof(std::string), sdesktop::cdc_queue_len},
+ {{sdesktop::RECEIVE_QUEUE_BUFFER_NAME, sizeof(std::string *), sdesktop::cdc_queue_len},
{sdesktop::SEND_QUEUE_BUFFER_NAME, sizeof(std::string *), sdesktop::cdc_queue_object_size}});
if (ret == false) {
@@ 115,6 113,9 @@ sys::ReturnCodes ServiceDesktop::InitHandler()
return std::make_shared<sys::ResponseMessage>();
});
+ settings->registerValueChange(updateos::settings::history,
+ [this](const std::string &value) { updateOS->setInitialHistory(value); });
+
return (sys::ReturnCodes::Success);
}
M module-services/service-desktop/WorkerDesktop.cpp => module-services/service-desktop/WorkerDesktop.cpp +5 -6
@@ 30,7 30,7 @@ bool WorkerDesktop::init(std::list<sys::WorkerQueueInfo> queues)
Worker::init(queues);
receiveQueue = Worker::getQueueHandleByName(sdesktop::RECEIVE_QUEUE_BUFFER_NAME);
- parserFSM::MessageHandler::sendQueue = Worker::getQueueHandleByName(sdesktop::SEND_QUEUE_BUFFER_NAME);
+ parserFSM::MessageHandler::setSendQueueHandle(Worker::getQueueHandleByName(sdesktop::SEND_QUEUE_BUFFER_NAME));
return (bsp::usbInit(receiveQueue, this) < 0) ? false : true;
}
@@ 58,16 58,17 @@ bool WorkerDesktop::handleMessage(uint32_t queueID)
LOG_INFO("handleMessage received data from queue: %s", qname.c_str());
- static std::string *sendMsg = nullptr;
- static std::string receivedMsg;
if (qname == sdesktop::RECEIVE_QUEUE_BUFFER_NAME) {
+ std::string *receivedMsg = nullptr;
if (!queue->Dequeue(&receivedMsg, 0)) {
LOG_ERROR("handleMessage failed to receive from \"%s\"", sdesktop::RECEIVE_QUEUE_BUFFER_NAME);
return false;
}
- parser.processMessage(receivedMsg);
+ parser.processMessage(std::move(*receivedMsg));
+ delete receivedMsg;
}
else if (qname == sdesktop::SEND_QUEUE_BUFFER_NAME) {
+ std::string *sendMsg = nullptr;
if (!queue->Dequeue(&sendMsg, 0)) {
LOG_ERROR("handleMessage xQueueReceive failed for %s.", sdesktop::SEND_QUEUE_BUFFER_NAME);
return false;
@@ 75,9 76,7 @@ bool WorkerDesktop::handleMessage(uint32_t queueID)
LOG_DEBUG("handeMessage sending %d bytes using usbCDCSend", static_cast<unsigned int>(sendMsg->length()));
bsp::usbCDCSend(sendMsg);
-
delete sendMsg;
- sendMsg = nullptr;
}
else {
LOG_INFO("handeMessage got message on an unhandled queue");
M module-services/service-desktop/endpoints/EndpointFactory.hpp => module-services/service-desktop/endpoints/EndpointFactory.hpp +13 -14
@@ 19,36 19,35 @@
#include "restore/RestoreEndpoint.hpp"
#include "update/UpdateEndpoint.hpp"
-using namespace parserFSM;
-
class EndpointFactory
{
public:
- static auto create(Context &context, sys::Service *ownerServicePtr) -> std::unique_ptr<Endpoint>
+ static auto create(parserFSM::Context &context, sys::Service *ownerServicePtr)
+ -> std::unique_ptr<parserFSM::Endpoint>
{
LOG_DEBUG("Creating endpoint: %d", static_cast<int>(context.getEndpoint()));
switch (context.getEndpoint()) {
- case EndpointType::update:
+ case parserFSM::EndpointType::update:
return std::make_unique<UpdateEndpoint>(ownerServicePtr);
- case EndpointType::filesystemUpload:
+ case parserFSM::EndpointType::filesystemUpload:
return std::make_unique<FilesystemEndpoint>(ownerServicePtr);
- case EndpointType::backup:
+ case parserFSM::EndpointType::backup:
return std::make_unique<BackupEndpoint>(ownerServicePtr);
- case EndpointType::deviceInfo:
+ case parserFSM::EndpointType::deviceInfo:
return std::make_unique<DeviceInfoEndpoint>(ownerServicePtr);
- case EndpointType::restore:
+ case parserFSM::EndpointType::restore:
return std::make_unique<RestoreEndpoint>(ownerServicePtr);
- case EndpointType::contacts:
+ case parserFSM::EndpointType::contacts:
return std::make_unique<ContactsEndpoint>(ownerServicePtr);
- case EndpointType::messages:
+ case parserFSM::EndpointType::messages:
return std::make_unique<MessagesEndpoint>(ownerServicePtr);
- case EndpointType::factory:
+ case parserFSM::EndpointType::factory:
return std::make_unique<FactoryResetEndpoint>(ownerServicePtr);
- case EndpointType::calllog:
+ case parserFSM::EndpointType::calllog:
return std::make_unique<CalllogEndpoint>(ownerServicePtr);
- case EndpointType::developerMode:
+ case parserFSM::EndpointType::developerMode:
return std::make_unique<DeveloperModeEndpoint>(ownerServicePtr);
- case EndpointType::calendarEvents:
+ case parserFSM::EndpointType::calendarEvents:
return std::make_unique<CalendarEventsEndpoint>(ownerServicePtr);
default:
return nullptr;
M module-services/service-desktop/endpoints/backup/BackupEndpoint.cpp => module-services/service-desktop/endpoints/backup/BackupEndpoint.cpp +2 -0
@@ 18,6 18,8 @@
static bool backupReady = false;
+using namespace parserFSM;
+
auto BackupEndpoint::handle(Context &context) -> void
{
switch (context.getMethod()) {
M module-services/service-desktop/endpoints/backup/BackupEndpoint.hpp => module-services/service-desktop/endpoints/backup/BackupEndpoint.hpp +4 -6
@@ 20,16 20,14 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class BackupEndpoint : public Endpoint
+class BackupEndpoint : public parserFSM::Endpoint
{
public:
BackupEndpoint(sys::Service *ownerServicePtr) : Endpoint(ownerServicePtr)
{
debugName = "BackupEndpoint";
}
- auto handle(Context &context) -> void override;
- auto request(Context &context) -> sys::ReturnCodes;
- auto upload(Context &context) -> sys::ReturnCodes;
+ auto handle(parserFSM::Context &context) -> void override;
+ auto request(parserFSM::Context &context) -> sys::ReturnCodes;
+ auto upload(parserFSM::Context &context) -> sys::ReturnCodes;
};
M module-services/service-desktop/endpoints/calendarEvents/CalendarEventsEndpoint.hpp => module-services/service-desktop/endpoints/calendarEvents/CalendarEventsEndpoint.hpp +4 -6
@@ 7,18 7,16 @@
#include "Service/Service.hpp"
#include "CalendarEventsHelper.hpp"
-using namespace parserFSM;
-
-class CalendarEventsEndpoint : public Endpoint
+class CalendarEventsEndpoint : public parserFSM::Endpoint
{
private:
std::string debugName = "CalendarEventsEndpoint";
- std::unique_ptr<CalendarEventsHelper> helper;
+ std::unique_ptr<parserFSM::CalendarEventsHelper> helper;
public:
CalendarEventsEndpoint(sys::Service *_ownerServicePtr) : Endpoint(_ownerServicePtr)
{
- helper = std::make_unique<CalendarEventsHelper>(ownerServicePtr);
+ helper = std::make_unique<parserFSM::CalendarEventsHelper>(ownerServicePtr);
}
- void handle(Context &context) override;
+ void handle(parserFSM::Context &context) override;
};
M module-services/service-desktop/endpoints/calllog/CalllogEndpoint.hpp => module-services/service-desktop/endpoints/calllog/CalllogEndpoint.hpp +4 -6
@@ 20,18 20,16 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class CalllogEndpoint : public Endpoint
+class CalllogEndpoint : public parserFSM::Endpoint
{
private:
- std::unique_ptr<CalllogHelper> helper;
+ std::unique_ptr<parserFSM::CalllogHelper> helper;
public:
CalllogEndpoint(sys::Service *_ownerServicePtr) : Endpoint(_ownerServicePtr)
{
debugName = "CalllogEndpoint";
- helper = std::make_unique<CalllogHelper>(ownerServicePtr);
+ helper = std::make_unique<parserFSM::CalllogHelper>(ownerServicePtr);
}
- auto handle(Context &context) -> void override;
+ auto handle(parserFSM::Context &context) -> void override;
};
M module-services/service-desktop/endpoints/contacts/ContactsEndpoint.hpp => module-services/service-desktop/endpoints/contacts/ContactsEndpoint.hpp +4 -6
@@ 22,18 22,16 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class ContactsEndpoint : public Endpoint
+class ContactsEndpoint : public parserFSM::Endpoint
{
private:
- std::unique_ptr<ContactHelper> helper;
+ std::unique_ptr<parserFSM::ContactHelper> helper;
public:
ContactsEndpoint(sys::Service *_ownerServicePtr) : Endpoint(_ownerServicePtr)
{
debugName = "ContactsEndpoint";
- helper = std::make_unique<ContactHelper>(ownerServicePtr);
+ helper = std::make_unique<parserFSM::ContactHelper>(ownerServicePtr);
}
- auto handle(Context &context) -> void override;
+ auto handle(parserFSM::Context &context) -> void override;
};
M module-services/service-desktop/endpoints/developerMode/DeveloperModeEndpoint.hpp => module-services/service-desktop/endpoints/developerMode/DeveloperModeEndpoint.hpp +4 -6
@@ 21,18 21,16 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class DeveloperModeEndpoint : public Endpoint
+class DeveloperModeEndpoint : public parserFSM::Endpoint
{
private:
- std::unique_ptr<DeveloperModeHelper> helper;
+ std::unique_ptr<parserFSM::DeveloperModeHelper> helper;
public:
DeveloperModeEndpoint(sys::Service *_ownerServicePtr) : Endpoint(_ownerServicePtr)
{
debugName = "DeveloperModeEndpoint";
- helper = std::make_unique<DeveloperModeHelper>(ownerServicePtr);
+ helper = std::make_unique<parserFSM::DeveloperModeHelper>(ownerServicePtr);
}
- auto handle(Context &context) -> void override;
+ auto handle(parserFSM::Context &context) -> void override;
};
M module-services/service-desktop/endpoints/deviceInfo/DeviceInfoEndpoint.cpp => module-services/service-desktop/endpoints/deviceInfo/DeviceInfoEndpoint.cpp +2 -0
@@ 13,6 13,8 @@
#include <cstdint>
#include <string>
+using namespace parserFSM;
+
auto DeviceInfoEndpoint::handle(Context &context) -> void
{
switch (context.getMethod()) {
M module-services/service-desktop/endpoints/deviceInfo/DeviceInfoEndpoint.hpp => module-services/service-desktop/endpoints/deviceInfo/DeviceInfoEndpoint.hpp +3 -5
@@ 19,9 19,7 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class DeviceInfoEndpoint : public Endpoint
+class DeviceInfoEndpoint : public parserFSM::Endpoint
{
public:
@@ 29,6 27,6 @@ class DeviceInfoEndpoint : public Endpoint
{
debugName = "DeviceInfoEndpoint";
}
- auto handle(Context &context) -> void override;
- auto getDeviceInfo(Context &context) -> bool;
+ auto handle(parserFSM::Context &context) -> void override;
+ auto getDeviceInfo(parserFSM::Context &context) -> bool;
};
M module-services/service-desktop/endpoints/factoryReset/FactoryResetEndpoint.cpp => module-services/service-desktop/endpoints/factoryReset/FactoryResetEndpoint.cpp +3 -3
@@ 13,7 13,7 @@
#include <memory>
-auto FactoryResetEndpoint::handle(Context &context) -> void
+auto FactoryResetEndpoint::handle(parserFSM::Context &context) -> void
{
if (context.getMethod() == parserFSM::http::Method::post) {
@@ 27,14 27,14 @@ auto FactoryResetEndpoint::handle(Context &context) -> void
context.setResponseBody(json11::Json::object({{parserFSM::json::factoryRequest, false}}));
}
- MessageHandler::putToSendQueue(context.createSimpleResponse());
+ parserFSM::MessageHandler::putToSendQueue(context.createSimpleResponse());
return;
}
else {
context.setResponseBody(json11::Json::object({{parserFSM::json::factoryRequest, false}}));
- MessageHandler::putToSendQueue(context.createSimpleResponse());
+ parserFSM::MessageHandler::putToSendQueue(context.createSimpleResponse());
return;
}
M module-services/service-desktop/endpoints/factoryReset/FactoryResetEndpoint.hpp => module-services/service-desktop/endpoints/factoryReset/FactoryResetEndpoint.hpp +3 -5
@@ 19,9 19,7 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class FactoryResetEndpoint : public Endpoint
+class FactoryResetEndpoint : public parserFSM::Endpoint
{
public:
@@ 29,6 27,6 @@ class FactoryResetEndpoint : public Endpoint
{
debugName = "FactoryResetEndpoint";
}
- auto handle(Context &context) -> void override;
- auto makeFactoryReset(Context &context) -> bool;
+ auto handle(parserFSM::Context &context) -> void override;
+ auto makeFactoryReset(parserFSM::Context &context) -> bool;
};
M module-services/service-desktop/endpoints/filesystem/FilesystemEndpoint.cpp => module-services/service-desktop/endpoints/filesystem/FilesystemEndpoint.cpp +3 -1
@@ 6,6 6,8 @@
#include "service-desktop/ServiceDesktop.hpp"
#include <purefs/filesystem_paths.hpp>
+using namespace parserFSM;
+
auto FilesystemEndpoint::handle(Context &context) -> void
{
LOG_DEBUG("handle");
@@ 68,4 70,4 @@ auto FilesystemEndpoint::run(Context &context) -> sys::ReturnCodes
MessageHandler::putToSendQueue(context.createSimpleResponse());
return returnCode;
-}>
\ No newline at end of file
+}
M module-services/service-desktop/endpoints/filesystem/FilesystemEndpoint.hpp => module-services/service-desktop/endpoints/filesystem/FilesystemEndpoint.hpp +4 -6
@@ 6,14 6,12 @@
#include <module-services/service-desktop/endpoints/Endpoint.hpp>
#include "Service/Service.hpp"
-using namespace parserFSM;
-
-class FilesystemEndpoint : public Endpoint
+class FilesystemEndpoint : public parserFSM::Endpoint
{
public:
FilesystemEndpoint(sys::Service *ownerServicePtr) : Endpoint(ownerServicePtr)
{}
- auto handle(Context &context) -> void override;
- auto run(Context &context) -> sys::ReturnCodes;
- auto getUpdates(Context &context) -> sys::ReturnCodes;
+ auto handle(parserFSM::Context &context) -> void override;
+ auto run(parserFSM::Context &context) -> sys::ReturnCodes;
+ auto getUpdates(parserFSM::Context &context) -> sys::ReturnCodes;
};
M module-services/service-desktop/endpoints/messages/MessagesEndpoint.hpp => module-services/service-desktop/endpoints/messages/MessagesEndpoint.hpp +4 -6
@@ 21,18 21,16 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class MessagesEndpoint : public Endpoint
+class MessagesEndpoint : public parserFSM::Endpoint
{
private:
- std::shared_ptr<MessageHelper> helper;
+ std::shared_ptr<parserFSM::MessageHelper> helper;
public:
MessagesEndpoint(sys::Service *_ownerServicePtr) : Endpoint(_ownerServicePtr)
{
debugName = "MessagesEndpoint";
- helper = std::make_shared<MessageHelper>(ownerServicePtr);
+ helper = std::make_shared<parserFSM::MessageHelper>(ownerServicePtr);
}
- auto handle(Context &context) -> void override;
+ auto handle(parserFSM::Context &context) -> void override;
};
M module-services/service-desktop/endpoints/restore/RestoreEndpoint.cpp => module-services/service-desktop/endpoints/restore/RestoreEndpoint.cpp +2 -0
@@ 14,6 14,8 @@
#include <memory>
+using namespace parserFSM;
+
auto RestoreEndpoint::handle(Context &context) -> void
{
if (context.getMethod() == parserFSM::http::Method::post) {
M module-services/service-desktop/endpoints/restore/RestoreEndpoint.hpp => module-services/service-desktop/endpoints/restore/RestoreEndpoint.hpp +2 -4
@@ 16,14 16,12 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class RestoreEndpoint : public Endpoint
+class RestoreEndpoint : public parserFSM::Endpoint
{
public:
RestoreEndpoint(sys::Service *ownerServicePtr) : Endpoint(ownerServicePtr)
{
debugName = "RestoreEndpoint";
}
- auto handle(Context &context) -> void override;
+ auto handle(parserFSM::Context &context) -> void override;
};
M module-services/service-desktop/endpoints/update/UpdateEndpoint.cpp => module-services/service-desktop/endpoints/update/UpdateEndpoint.cpp +2 -0
@@ 17,6 17,8 @@
#include <filesystem>
#include <memory>
+using namespace parserFSM;
+
auto UpdateEndpoint::handle(Context &context) -> void
{
switch (context.getMethod()) {
M module-services/service-desktop/endpoints/update/UpdateEndpoint.hpp => module-services/service-desktop/endpoints/update/UpdateEndpoint.hpp +4 -6
@@ 20,9 20,7 @@ namespace sys
class Service;
} // namespace sys
-using namespace parserFSM;
-
-class UpdateEndpoint : public Endpoint
+class UpdateEndpoint : public parserFSM::Endpoint
{
public:
@@ 30,7 28,7 @@ class UpdateEndpoint : public Endpoint
{
debugName = "UpdateEndpoint";
}
- auto handle(Context &context) -> void override;
- auto run(Context &context) -> sys::ReturnCodes;
- auto getUpdates(Context &context) -> sys::ReturnCodes;
+ auto handle(parserFSM::Context &context) -> void override;
+ auto run(parserFSM::Context &context) -> sys::ReturnCodes;
+ auto getUpdates(parserFSM::Context &context) -> sys::ReturnCodes;
};
M module-services/service-desktop/parser/MessageHandler.cpp => module-services/service-desktop/parser/MessageHandler.cpp +3 -3
@@ 23,7 23,7 @@ using namespace parserFSM;
xQueueHandle MessageHandler::sendQueue;
-MessageHandler::MessageHandler(std::string &message, sys::Service *OwnerService) : OwnerServicePtr(OwnerService)
+MessageHandler::MessageHandler(const std::string &message, sys::Service *OwnerService) : OwnerServicePtr(OwnerService)
{
try {
messageJson = json11::Json::parse(message, JsonErrorMsg);
@@ 53,10 53,10 @@ void MessageHandler::processMessage()
}
}
-void MessageHandler::putToSendQueue(const std::string msg)
+void MessageHandler::putToSendQueue(const std::string &msg)
{
if (uxQueueSpacesAvailable(sendQueue) != 0) {
- auto *responseString = new std::string(msg);
+ auto responseString = new std::string(msg);
xQueueSend(sendQueue, &responseString, portMAX_DELAY);
}
}
M module-services/service-desktop/parser/MessageHandler.hpp => module-services/service-desktop/parser/MessageHandler.hpp +14 -11
@@ 24,29 24,32 @@ namespace parserFSM
{
class MessageHandler
{
+ static xQueueHandle sendQueue;
+
+ json11::Json messageJson;
+ std::string JsonErrorMsg;
+ sys::Service *OwnerServicePtr = nullptr;
public:
- MessageHandler(std::string &message, sys::Service *OwnerService);
- static xQueueHandle sendQueue;
+ MessageHandler(const std::string &message, sys::Service *OwnerService);
- bool isJSONNull()
+ [[nodiscard]] auto isJSONNull() const -> bool
{
return messageJson.is_null();
};
- bool isValid()
+ [[nodiscard]] auto isValid() const noexcept -> bool
{
return JsonErrorMsg.empty();
}
- std::string &getErrorString()
+ [[nodiscard]] auto getErrorString() const -> const std::string &
{
return JsonErrorMsg;
};
void processMessage();
- static void putToSendQueue(const std::string msg);
-
- private:
- json11::Json messageJson;
- std::string JsonErrorMsg;
- sys::Service *OwnerServicePtr = nullptr;
+ static void putToSendQueue(const std::string &msg);
+ static void setSendQueueHandle(xQueueHandle handle)
+ {
+ sendQueue = handle;
+ }
};
} // namespace parserFSM
M module-services/service-desktop/parser/ParserFSM.cpp => module-services/service-desktop/parser/ParserFSM.cpp +23 -23
@@ 28,10 28,10 @@ using namespace parserFSM;
StateMachine::StateMachine(sys::Service *OwnerService) : OwnerServicePtr(OwnerService)
{}
-void StateMachine::processMessage(std::string &msg)
+void StateMachine::processMessage(std::string &&msg)
{
- receivedMsgPtr = &msg;
- LOG_DEBUG("Msg: %s", receivedMsgPtr->c_str());
+ receivedMsg = std::move(msg);
+ LOG_DEBUG("Msg: %s", receivedMsg.c_str());
switch (state) {
case State::ReceivedPayload:
@@ 58,20 58,20 @@ void StateMachine::parseHeader()
header.clear();
payloadLength = 0;
- auto messageStart = receivedMsgPtr->find(message::endpointChar);
+ auto messageStart = receivedMsg.find(message::endpointChar);
if (messageStart == std::string::npos) {
- LOG_ERROR("This is not a valid endpoint message! Type=%c", receivedMsgPtr->at(0));
+ LOG_ERROR("This is not a valid endpoint message! Type=%c", receivedMsg.at(0));
return;
}
- if (receivedMsgPtr->size() < message::size_header) // header divided in few parts
+ if (receivedMsg.size() < message::size_header) // header divided in few parts
{
state = State::ReceivedPartialHeader;
- header.append(*receivedMsgPtr); // append to whole header string
+ header.append(receivedMsg); // append to whole header string
return;
}
- header = message::getHeader(*receivedMsgPtr);
+ header = message::getHeader(receivedMsg);
payloadLength = message::calcPayloadLength(header);
if (payloadLength == 0) // failed to obtain payload length from msg
{
@@ 82,7 82,7 @@ void StateMachine::parseHeader()
LOG_DEBUG("Payload length: %lu", payloadLength);
- message::removeHeader(*receivedMsgPtr);
+ message::removeHeader(receivedMsg);
parseNewMessage();
}
@@ 91,39 91,39 @@ void StateMachine::parsePartialHeader()
auto previousHeaderLength = header.size();
auto missingHeaderLength = message::size_header - previousHeaderLength;
- if (receivedMsgPtr->size() >= missingHeaderLength) // rest of the message is here
+ if (receivedMsg.size() >= missingHeaderLength) // rest of the message is here
{
- header.append(receivedMsgPtr->substr(0, missingHeaderLength));
+ header.append(receivedMsg.substr(0, missingHeaderLength));
LOG_DEBUG("Header: %s\n", header.c_str());
payloadLength = message::calcPayloadLength(header);
LOG_DEBUG("Payload length: %lu\n", payloadLength);
- message::eraseFront(*receivedMsgPtr, missingHeaderLength);
+ message::eraseFront(receivedMsg, missingHeaderLength);
parseNewMessage();
}
else // the message is even longer :(
{
- header.append(*receivedMsgPtr);
+ header.append(receivedMsg);
}
}
void StateMachine::parseNewMessage()
{
- if (receivedMsgPtr->size() >= payloadLength) {
+ if (receivedMsg.size() >= payloadLength) {
- payload = message::extractPayload(*receivedMsgPtr, payloadLength);
+ payload = message::extractPayload(receivedMsg, payloadLength);
parsePayload();
- if (receivedMsgPtr->size() > payloadLength) { // contains part of new header
- message::eraseFront(*receivedMsgPtr, payloadLength);
+ if (receivedMsg.size() > payloadLength) { // contains part of new header
+ message::eraseFront(receivedMsg, payloadLength);
parseHeader();
}
}
else // message divided in 2 or more packets
{
- payload = receivedMsgPtr->substr(0, std::string::npos); // take rest of the message
+ payload = receivedMsg.substr(0, std::string::npos); // take rest of the message
state = State::ReceivedPartialPayload;
}
}
@@ 133,20 133,20 @@ void StateMachine::parsePartialMessage()
auto previousPayloadLength = payload.size();
auto missingPayloadLength = payloadLength - previousPayloadLength;
- if (receivedMsgPtr->size() >= missingPayloadLength) // rest of the message is here
+ if (receivedMsg.size() >= missingPayloadLength) // rest of the message is here
{
- payload.append(message::extractPayload(*receivedMsgPtr, missingPayloadLength));
+ payload.append(message::extractPayload(receivedMsg, missingPayloadLength));
parsePayload();
- if (receivedMsgPtr->size() > missingPayloadLength) {
- message::eraseFront(*receivedMsgPtr, missingPayloadLength);
+ if (receivedMsg.size() > missingPayloadLength) {
+ message::eraseFront(receivedMsg, missingPayloadLength);
parseHeader();
}
}
else // the message is even longer
{
- payload.append(*receivedMsgPtr);
+ payload.append(receivedMsg);
}
}
M module-services/service-desktop/parser/ParserFSM.hpp => module-services/service-desktop/parser/ParserFSM.hpp +6 -6
@@ 23,21 23,21 @@ namespace parserFSM
class StateMachine
{
public:
- StateMachine(sys::Service *OwnerService);
- void processMessage(std::string &msg);
- State getCurrentState()
+ explicit StateMachine(sys::Service *OwnerService);
+ void processMessage(std::string &&msg);
+ [[nodiscard]] auto getCurrentState() const noexcept -> State
{
return state;
};
- void setState(const parserFSM::State newState)
+ void setState(const parserFSM::State newState) noexcept
{
state = newState;
}
private:
- std::string *receivedMsgPtr = nullptr;
- parserFSM::State state = State::NoMsg;
+ std::string receivedMsg;
+ parserFSM::State state = State::NoMsg;
std::string payload;
std::string header;
unsigned long payloadLength = 0;
M module-services/service-desktop/service-desktop/DesktopMessages.hpp => module-services/service-desktop/service-desktop/DesktopMessages.hpp +1 -1
@@ 71,7 71,7 @@ namespace sdesktop
class Event
{
protected:
- Context context;
+ parserFSM::Context context;
public:
void send();
M module-services/service-desktop/tests/unittest.cpp => module-services/service-desktop/tests/unittest.cpp +25 -21
@@ 68,76 68,80 @@ using namespace parserFSM;
TEST_CASE("Parser Test")
{
StateMachine parser(nullptr);
- std::string testMessage("#00000");
SECTION("Parse message with divided header and payload")
{
- parser.processMessage(testMessage);
+ std::string testMessage("#00000");
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPartialHeader);
testMessage = R"(0050{"endpo)";
- parser.processMessage(testMessage);
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPartialPayload);
testMessage = R"(int":1, "method":1, "body":{"test":"test"}})";
- parser.processMessage(testMessage);
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPayload);
}
SECTION("Parse whole message")
{
- testMessage = R"(#000000050{"endpoint":1, "method":1, "body":{"test":"test"}})";
- parser.processMessage(testMessage);
+ std::string testMessage = R"(#000000050{"endpoint":1, "method":1, "body":{"test":"test"}})";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPayload);
}
SECTION("Parse message with start char detached from mesage")
{
- testMessage = R"(#)";
- parser.processMessage(testMessage);
+ std::string testMessage = R"(#)";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPartialHeader);
testMessage = R"(000000050{"en)";
- parser.processMessage(testMessage);
+ testMessage = R"(000000050{"en)";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPartialPayload);
testMessage = R"(dpoint":1, "method":1, "body":{"test":"test"}})";
- parser.processMessage(testMessage);
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPayload);
}
SECTION("Parse message with beginning of another one")
{
- testMessage = R"(#000000050{"endpoint":1, "method":1, "body":{"test":"test"}}#000000050{"end)";
- parser.processMessage(testMessage);
+ std::string testMessage = R"(#000000050{"endpoint":1, "method":1, "body":{"test":"test"}}#000000050{"end)";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPartialPayload);
testMessage = R"(point":1, "method":1, "body":{"test":"test"}})";
- parser.processMessage(testMessage);
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::ReceivedPayload);
}
SECTION("Parse junk message")
{
- testMessage = R"({"address": "6 Czeczota St.\n02600 Warsaw"})";
- parser.processMessage(testMessage);
+ std::string testMessage = R"({"address": "6 Czeczota St.\n02600 Warsaw"})";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::NoMsg);
}
SECTION("Parse message with incorrect header length")
{
- testMessage = R"(#000000072{"endpoint":7, "method":2, "uuid":3, "body":{"threadID":1,"unread":false}})";
- parser.processMessage(testMessage);
+ std::string testMessage =
+ R"(#000000072{"endpoint":7, "method":2, "uuid":3, "body":{"threadID":1,"unread":false}})";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::NoMsg);
}
SECTION("Parse message with damaged json ")
{
- testMessage = R"(#000000074{"endpoint":7, "method":2, "uuid":3, "bo}}dy":{"threadID":1,"unread":false)";
- parser.processMessage(testMessage);
+ std::string testMessage =
+ R"(#000000074{"endpoint":7, "method":2, "uuid":3, "bo}}dy":{"threadID":1,"unread":false)";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::NoMsg);
}
SECTION("Parse message with damaged json and incorrect header length")
{
- testMessage = R"(#000000072{"endpoint":7, "method":2, "uuid":3, "bo}}dy":{"threadID":1,"unread":false)";
- parser.processMessage(testMessage);
+ std::string testMessage =
+ R"(#000000072{"endpoint":7, "method":2, "uuid":3, "bo}}dy":{"threadID":1,"unread":false)";
+ parser.processMessage(std::move(testMessage));
REQUIRE(parser.getCurrentState() == State::NoMsg);
}
}
M module-services/service-eink/EinkDisplay.cpp => module-services/service-eink/EinkDisplay.cpp +2 -2
@@ 85,8 85,8 @@ namespace service::eink
EinkBpp_e EinkDisplay::getCurrentBitsPerPixelFormat() const noexcept
{
- if (waveformSettings.mode == EinkWaveformDU2) {
- return Eink1Bpp;
+ if ((waveformSettings.mode == EinkWaveformA2) || (waveformSettings.mode == EinkWaveformDU2)) {
+ return Eink4Bpp; /// this should be 1Bpp, but the OS is not ready for this
}
return Eink4Bpp;
}
M module-services/service-eink/board/linux/renderer/CMakeLists.txt => module-services/service-eink/board/linux/renderer/CMakeLists.txt +3 -1
@@ 4,6 4,8 @@ project( service_renderer VERSION 1.0
DESCRIPTION "GTK application for showing draw buffer."
LANGUAGES CXX )
+include(Utils)
+
find_package(PkgConfig REQUIRED)
pkg_check_modules(GTKMM REQUIRED gtkmm-3.0)
@@ 14,7 16,7 @@ add_executable( ${PROJECT_NAME}
${CMAKE_CURRENT_SOURCE_DIR}/src/RArea.hpp
${CMAKE_CURRENT_SOURCE_DIR}/src/RWindow.hpp )
-install(TARGETS ${PROJECT_NAME} DESTINATION "./")
+install(TARGETS ${PROJECT_NAME} DESTINATION "./" COMPONENT Standalone)
target_link_libraries( ${PROJECT_NAME} ${GTKMM_LIBRARIES} )
target_include_directories(${PROJECT_NAME} PUBLIC ${GTKMM_LIBRARY_DIRS} )
M module-services/service-evtmgr/CMakeLists.txt => module-services/service-evtmgr/CMakeLists.txt +2 -2
@@ 7,9 7,9 @@ set(SOURCES
alarm/EventManagerAlarm.cpp
api/EventManagerServiceAPI.cpp
messages/Message.cpp
- screen-light-control/ScreenLightControl.cpp
- screen-light-control/ControlFunctions.cpp
battery-level-check/BatteryLevelCheck.cpp
+ screen-light-control/ControlFunctions.cpp
+ screen-light-control/ScreenLightControl.cpp
)
add_library(${PROJECT_NAME} STATIC ${SOURCES})
M module-services/service-evtmgr/EventManager.cpp => module-services/service-evtmgr/EventManager.cpp +20 -13
@@ 2,13 2,15 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "service-evtmgr/BatteryMessages.hpp"
-#include "service-evtmgr/Constants.hpp"
#include "service-evtmgr/EVMessages.hpp"
-#include "service-evtmgr/EventManager.hpp"
#include "service-evtmgr/KbdMessage.hpp"
+#include "service-evtmgr/ScreenLightControlMessage.hpp"
+#include "service-evtmgr/Constants.hpp"
+#include "service-evtmgr/EventManager.hpp"
#include "service-evtmgr/WorkerEvent.hpp"
-#include "screen-light-control/ScreenLightControl.hpp"
+
#include "battery-level-check/BatteryLevelCheck.hpp"
+#include "screen-light-control/ScreenLightControl.hpp"
#include <BaseInterface.hpp>
#include <MessageType.hpp>
@@ 39,7 41,8 @@
#include <module-apps/messages/AppMessage.hpp>
#include <SystemManager/messages/CpuFrequencyMessage.hpp>
-EventManager::EventManager(const std::string &name) : sys::Service(name)
+EventManager::EventManager(const std::string &name)
+ : sys::Service(name), screenLightControl(std::make_unique<screen_light_control::ScreenLightControl>(this))
{
LOG_INFO("[%s] Initializing", name.c_str());
alarmTimestamp = 0;
@@ 261,12 264,6 @@ sys::ReturnCodes EventManager::InitHandler()
return response;
});
- connect(sevm::ScreenLightControlMessage(sevm::screen_light_control::Action::turnOff), [&](sys::Message *msgl) {
- auto request = static_cast<sevm::ScreenLightControlMessage *>(msgl);
- sevm::screen_light_control::processRequest(request->action, request->parameters);
- return std::make_shared<sys::ResponseMessage>();
- });
-
connect(sevm::BatterySetCriticalLevel(0), [&](sys::Message *msgl) {
auto request = static_cast<sevm::BatterySetCriticalLevel *>(msgl);
battery_level_check::setBatteryCriticalLevel(request->criticalLevel);
@@ 278,6 275,19 @@ sys::ReturnCodes EventManager::InitHandler()
return std::make_shared<sys::ResponseMessage>();
});
+ connect(sevm::ScreenLightControlMessage(), [&](sys::Message *msgl) {
+ auto *m = dynamic_cast<sevm::ScreenLightControlMessage *>(msgl);
+ screenLightControl->processRequest(m->action, m->parameters);
+ return std::make_shared<sys::ResponseMessage>();
+ });
+
+ connect(sevm::ScreenLightControlRequestParameters(), [&](sys::Message *msgl) {
+ screen_light_control::Parameters params = {screenLightControl->getBrightnessValue()};
+ auto msg = std::make_shared<sevm::ScreenLightControlParametersResponse>(
+ screenLightControl->getLightState(), screenLightControl->getAutoModeState(), params);
+ return msg;
+ });
+
// initialize keyboard worker
EventWorker = std::make_unique<WorkerEvent>(this);
@@ 312,14 322,12 @@ sys::ReturnCodes EventManager::InitHandler()
EventWorker->init(list);
EventWorker->run();
- sevm::screen_light_control::init(this);
return sys::ReturnCodes::Success;
}
sys::ReturnCodes EventManager::DeinitHandler()
{
- sevm::screen_light_control::deinit();
EventWorker->close();
EventWorker.reset();
EventWorker = nullptr;
@@ 344,7 352,6 @@ sys::ReturnCodes EventManager::SwitchPowerModeHandler(const sys::ServicePowerMod
bool EventManager::messageSetApplication(sys::Service *sender, const std::string &applicationName)
{
-
auto msg = std::make_shared<sevm::EVMFocusApplication>(applicationName);
return sys::Bus::SendUnicast(msg, service::name::evt_manager, sender);
}
M module-services/service-evtmgr/WorkerEvent.cpp => module-services/service-evtmgr/WorkerEvent.cpp +13 -16
@@ 2,9 2,9 @@
// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
#include "service-evtmgr/BatteryMessages.hpp"
-#include "service-evtmgr/Constants.hpp"
#include "service-evtmgr/EVMessages.hpp"
#include "service-evtmgr/KbdMessage.hpp"
+#include "service-evtmgr/Constants.hpp"
#include "service-evtmgr/WorkerEvent.hpp"
#include "battery-level-check/BatteryLevelCheck.hpp"
@@ 78,7 78,7 @@ bool WorkerEvent::handleMessage(uint32_t queueID)
}
if (bsp::headset::Handler(notification) == true) {
- bool state = bsp::headset::IsInserted();
+ bool state = bsp::headset::IsInserted();
auto message = std::make_shared<AudioEventRequest>(audio::EventType::JackState,
state ? audio::Event::DeviceState::Connected
: audio::Event::DeviceState::Disconnected);
@@ 91,28 91,25 @@ bool WorkerEvent::handleMessage(uint32_t queueID)
if (!queue->Dequeue(¬ification, 0)) {
return false;
}
- if (notification == static_cast<uint8_t>(bsp::batteryIRQSource::INTB)) {
+ if (notification == static_cast<uint8_t>(bsp::battery_charger::batteryIRQSource::INTB)) {
LOG_DEBUG("Battery INTB");
- const auto status = bsp::battery_getStatusRegister();
- if (status & static_cast<std::uint16_t>(bsp::batteryINTBSource::minVAlert)) {
+ const auto status = bsp::battery_charger::getStatusRegister();
+ if (status & static_cast<std::uint16_t>(bsp::battery_charger::batteryINTBSource::minVAlert)) {
auto messageBrownout = std::make_shared<sevm::BatteryBrownoutMessage>();
sys::Bus::SendUnicast(messageBrownout, service::name::system_manager, this->service);
}
- if (status & static_cast<std::uint16_t>(bsp::batteryINTBSource::SOCOnePercentChange)) {
- std::uint8_t battLevel = 0;
- bsp::battery_getBatteryLevel(battLevel);
+ if (status & static_cast<std::uint16_t>(bsp::battery_charger::batteryINTBSource::SOCOnePercentChange)) {
+ bsp::battery_charger::StateOfCharge battLevel = bsp::battery_charger::getBatteryLevel();
auto message = std::make_shared<sevm::BatteryLevelMessage>(battLevel, false);
sys::Bus::SendUnicast(message, service::name::evt_manager, this->service);
battery_level_check::checkBatteryLevelCritical();
}
- bsp::battery_ClearAllIRQs();
+ bsp::battery_charger::clearAllIRQs();
}
- if (notification == static_cast<uint8_t>(bsp::batteryIRQSource::INOKB)) {
- bool status;
- bsp::battery_getChargeStatus(status);
- bsp::battery_ClearAllIRQs();
+ if (notification == static_cast<uint8_t>(bsp::battery_charger::batteryIRQSource::INOKB)) {
+ bsp::battery_charger::clearAllIRQs();
auto message = std::make_shared<sevm::BatteryPlugMessage>();
- message->plugged = status;
+ message->plugged = bsp::battery_charger::getChargeStatus();
sys::Bus::SendUnicast(message, service::name::evt_manager, this->service);
}
}
@@ 193,7 190,7 @@ bool WorkerEvent::init(std::list<sys::WorkerQueueInfo> queuesList)
bsp::vibrator::init();
bsp::keyboard_Init(queues[static_cast<int32_t>(WorkerEventQueues::queueKeyboardIRQ)]->GetQueueHandle());
bsp::headset::Init(queues[static_cast<int32_t>(WorkerEventQueues::queueHeadsetIRQ)]->GetQueueHandle());
- bsp::battery_Init(queues[static_cast<int32_t>(WorkerEventQueues::queueBattery)]->GetQueueHandle());
+ bsp::battery_charger::init(queues[static_cast<int32_t>(WorkerEventQueues::queueBattery)]->GetQueueHandle());
bsp::rtc_Init(queues[static_cast<int32_t>(WorkerEventQueues::queueRTC)]->GetQueueHandle());
bsp::cellular::init(queues[static_cast<int32_t>(WorkerEventQueues::queueCellular)]->GetQueueHandle());
bsp::magnetometer::init(queues[static_cast<int32_t>(WorkerEventQueues::queueMagnetometerIRQ)]->GetQueueHandle());
@@ 216,7 213,7 @@ bool WorkerEvent::deinit(void)
Worker::deinit();
bsp::keyboard_Deinit();
bsp::headset::Deinit();
- bsp::battery_Deinit();
+ bsp::battery_charger::deinit();
bsp::torch::deinit();
bsp::keypad_backlight::deinit();
bsp::eink_frontlight::deinit();
M module-services/service-evtmgr/doc/screen_light_control.md => module-services/service-evtmgr/doc/screen_light_control.md +2 -1
@@ 54,6 54,7 @@ Default value of γ is 2.5 . For leds this factor could be in range 2.2-2.8
## Message API
-`sevm::ScreenLightControlMessage` is used to control the module. It takes action and data structure as parameters. Set of actions is described in `sevm::screen_light_control::Action`.
+`screen_light_control::ScreenLightControlMessage` is used to control the module. It takes action and data structure as parameters. Set of actions is described in `sevm::screen_light_control::Action`.
+`screen_light_control::ScreenLightControlRequestParameters` us ised to request currently setup parameters for display light and sensor.
=
\ No newline at end of file
M module-services/service-evtmgr/screen-light-control/ControlFunctions.cpp => module-services/service-evtmgr/screen-light-control/ControlFunctions.cpp +2 -2
@@ 4,7 4,7 @@
#include "ControlFunctions.hpp"
#include <cmath>
-namespace sevm::screen_light_control::functions
+namespace screen_light_control::functions
{
namespace
{
@@ 95,4 95,4 @@ namespace sevm::screen_light_control::functions
}
}
-} // namespace sevm::screen_light_control::functions
+} // namespace screen_light_control::functions
M module-services/service-evtmgr/screen-light-control/ControlFunctions.hpp => module-services/service-evtmgr/screen-light-control/ControlFunctions.hpp +2 -2
@@ 8,7 8,7 @@
#include <vector>
#include <memory>
-namespace sevm::screen_light_control::functions
+namespace screen_light_control::functions
{
using BrightnessFunction =
std::vector<std::pair<bsp::light_sensor::IlluminanceLux, bsp::eink_frontlight::BrightnessPercentage>>;
@@ 23,4 23,4 @@ namespace sevm::screen_light_control::functions
void setFunctionFromPoints(const BrightnessFunction &points);
-} // namespace sevm::screen_light_control::functions
+} // namespace screen_light_control::functions
M module-services/service-evtmgr/screen-light-control/ScreenLightControl.cpp => module-services/service-evtmgr/screen-light-control/ScreenLightControl.cpp +143 -75
@@ 3,119 3,99 @@
#include "ScreenLightControl.hpp"
-namespace sevm::screen_light_control
+#include <Service/Message.hpp>
+#include <Service/Service.hpp>
+#include <Service/Timer.hpp>
+#include <agents/settings/SystemSettings.hpp>
+
+namespace screen_light_control
{
namespace
{
- constexpr inline auto CONTROL_TIMER_MS = 25;
- constexpr inline auto READOUT_TIMER_MS = 500;
- std::unique_ptr<sys::Timer> controlTimer;
- std::unique_ptr<sys::Timer> readoutTimer;
-
- bool automaticMode = false;
- bool lightOn = false;
-
- void enableTimers()
- {
- controlTimer->connect([&](sys::Timer &) { controlTimerCallback(); });
- readoutTimer->connect([&](sys::Timer &) { readoutTimerCallback(); });
- controlTimer->start();
- readoutTimer->start();
- }
-
- void disableTimers()
+ auto from_string(const std::string &str, bool def) -> bool
{
- controlTimer->stop();
- readoutTimer->stop();
- }
-
- void setAutomaticModeParameters(const Parameters ¶ms)
- {
- if (lightOn && automaticMode) {
- disableTimers();
+ try {
+ return std::stoi(str) == 0;
}
-
- functions::setRampStep(100.0f *
- (static_cast<float>(CONTROL_TIMER_MS) / static_cast<float>(params.rampTimeMS)));
- functions::setHysteresis(params.brightnessHysteresis);
- functions::setFunctionFromPoints(params.functionPoints);
-
- if (lightOn && automaticMode) {
- enableTimers();
+ catch (std::exception &) {
+ return def;
}
}
- void turnOff()
+ auto from_string(const std::string &str, float def) -> float
{
- bsp::eink_frontlight::turnOff();
- bsp::light_sensor::standby();
- controlTimer->stop();
- readoutTimer->stop();
- lightOn = false;
- }
-
- void turnOn()
- {
- bsp::eink_frontlight::turnOn();
- bsp::light_sensor::wakeup();
- if (automaticMode) {
- enableTimers();
+ try {
+ return std::stof(str);
}
- lightOn = true;
- }
-
- void enableAutomaticMode()
- {
- if (lightOn) {
- enableTimers();
+ catch (std::exception &) {
+ return def;
}
- automaticMode = true;
}
-
- void disableAutomaticMode()
- {
- disableTimers();
- automaticMode = false;
- }
-
} // namespace
- void init(sys::Service *parent)
+ ScreenLightControl::ScreenLightControl(sys::Service *parent)
+ : settings(std::make_unique<settings::Settings>(parent))
{
controlTimer = std::make_unique<sys::Timer>("LightControlTimer", parent, CONTROL_TIMER_MS);
readoutTimer = std::make_unique<sys::Timer>("LightSensorReadoutTimer", parent, READOUT_TIMER_MS);
- Parameters defaultParams;
- setAutomaticModeParameters(defaultParams);
+ initFromSettings();
}
- void deinit()
+ ScreenLightControl::~ScreenLightControl()
{
disableTimers();
- controlTimer.reset();
- readoutTimer.reset();
}
- void processRequest(Action action, const Parameters ¶ms)
+ void ScreenLightControl::initFromSettings()
+ {
+ settings->registerValueChange(settings::Brightness::brightnessLevel,
+ [&](const std::string &value) { setBrightnessLevel(from_string(value, 0.0f)); });
+
+ settings->registerValueChange(settings::Brightness::autoMode, [&](const std::string &value) {
+ if (from_string(value, false)) {
+ enableAutomaticMode();
+ }
+ else {
+ disableAutomaticMode();
+ }
+ });
+
+ settings->registerValueChange(settings::Brightness::autoMode, [&](const std::string &value) {
+ if (from_string(value, false)) {
+ turnOn();
+ }
+ else {
+ turnOff();
+ }
+ });
+ }
+
+ void ScreenLightControl::processRequest(Action action, const Parameters ¶ms)
{
switch (action) {
case Action::turnOff:
turnOff();
+ setScreenLightSettings(settings::Brightness::state, lightOn);
break;
case Action::turnOn:
turnOn();
+ setScreenLightSettings(settings::Brightness::state, lightOn);
break;
case Action::enableAutomaticMode:
enableAutomaticMode();
+ setScreenLightSettings(settings::Brightness::autoMode, automaticMode);
break;
case Action::disableAutomaticMode:
disableAutomaticMode();
+ setScreenLightSettings(settings::Brightness::autoMode, automaticMode);
break;
case Action::setManualModeBrightness:
- bsp::eink_frontlight::setBrightness(params.manualModeBrightness);
+ setBrightnessLevel(params.manualModeBrightness);
+ setScreenLightSettings(settings::Brightness::brightnessLevel, params.manualModeBrightness);
break;
case Action::setGammaCorrectionFactor:
- bsp::eink_frontlight::setGammaFactor(params.gammaFactor);
+ setGammaFactor(params.gammaFactor);
break;
case Action::setAutomaticModeParameters:
setAutomaticModeParameters(params);
@@ 123,14 103,102 @@ namespace sevm::screen_light_control
}
}
- void controlTimerCallback()
+ void ScreenLightControl::controlTimerCallback()
{
bsp::eink_frontlight::setBrightness(functions::brightnessRampOut());
}
- void readoutTimerCallback()
+ void ScreenLightControl::readoutTimerCallback()
{
functions::calculateBrightness(bsp::light_sensor::readout());
}
-} // namespace sevm::screen_light_control
+ auto ScreenLightControl::getAutoModeState() const noexcept -> ScreenLightMode
+ {
+ return automaticMode;
+ }
+
+ auto ScreenLightControl::getLightState() const noexcept -> bool
+ {
+ return lightOn;
+ }
+
+ auto ScreenLightControl::getBrightnessValue() const noexcept -> bsp::eink_frontlight::BrightnessPercentage
+ {
+ return brightnessValue;
+ }
+
+ void ScreenLightControl::enableTimers()
+ {
+ controlTimer->connect([&](sys::Timer &) { controlTimerCallback(); });
+ readoutTimer->connect([&](sys::Timer &) { readoutTimerCallback(); });
+ controlTimer->start();
+ readoutTimer->start();
+ }
+
+ void ScreenLightControl::disableTimers()
+ {
+ controlTimer->stop();
+ readoutTimer->stop();
+ }
+
+ void ScreenLightControl::setAutomaticModeParameters(const Parameters ¶ms)
+ {
+ if (lightOn && automaticMode == ScreenLightMode::Automatic) {
+ disableTimers();
+ }
+
+ functions::setRampStep(100.0f * (static_cast<float>(CONTROL_TIMER_MS) / static_cast<float>(params.rampTimeMS)));
+ functions::setHysteresis(params.brightnessHysteresis);
+ functions::setFunctionFromPoints(params.functionPoints);
+
+ if (lightOn && automaticMode == ScreenLightMode::Automatic) {
+ enableTimers();
+ }
+ }
+
+ void ScreenLightControl::enableAutomaticMode()
+ {
+ if (lightOn) {
+ enableTimers();
+ }
+ automaticMode = ScreenLightMode::Automatic;
+ }
+
+ void ScreenLightControl::disableAutomaticMode()
+ {
+ disableTimers();
+ automaticMode = ScreenLightMode::Manual;
+ }
+
+ void ScreenLightControl::turnOn()
+ {
+ bsp::eink_frontlight::turnOn();
+ bsp::light_sensor::wakeup();
+ if (automaticMode) {
+ enableTimers();
+ }
+ lightOn = true;
+ }
+
+ void ScreenLightControl::setBrightnessLevel(bsp::eink_frontlight::BrightnessPercentage brightnessPercentage)
+ {
+ bsp::eink_frontlight::setBrightness(brightnessPercentage);
+ brightnessValue = brightnessPercentage;
+ }
+
+ void ScreenLightControl::setGammaFactor(float gammaFactor)
+ {
+ bsp::eink_frontlight::setGammaFactor(gammaFactor);
+ setScreenLightSettings(settings::Brightness::gammaFactor, gammaFactor);
+ }
+
+ void ScreenLightControl::turnOff()
+ {
+ bsp::eink_frontlight::turnOff();
+ bsp::light_sensor::standby();
+ controlTimer->stop();
+ readoutTimer->stop();
+ lightOn = false;
+ }
+} // namespace screen_light_control
M module-services/service-evtmgr/screen-light-control/ScreenLightControl.hpp => module-services/service-evtmgr/screen-light-control/ScreenLightControl.hpp +62 -10
@@ 3,13 3,26 @@
#pragma once
+#include <service-db/service-db/Settings.hpp>
#include "ControlFunctions.hpp"
-#include <Service/Timer.hpp>
+#include <Utils.hpp>
+
+namespace sys
+{
+ class Timer;
+}
/// Screen light control algorithm. Automatic/Manual mode of operation.
/// Processing of ambient light sensor input to screen brightness output.
-namespace sevm::screen_light_control
+namespace screen_light_control
{
+ /// Modes in which front light can operate
+ enum ScreenLightMode
+ {
+ Automatic, /// Automally sets screen brightness based on sensor data
+ Manual /// Manually set brightness level
+ };
+
/// Set of actions to control the screen light
enum class Action
{
@@ 24,6 37,8 @@ namespace sevm::screen_light_control
struct Parameters
{
+ static constexpr auto MAX_BRIGHTNESS = 100.0;
+
/// Screen brightness 0-100% in manual mode
bsp::eink_frontlight::BrightnessPercentage manualModeBrightness = 50.0f;
/// Vector of points for screen brightness [%] in relation to ambient light [Lux] function. Points have to be in
@@ 37,16 52,53 @@ namespace sevm::screen_light_control
float gammaFactor = 2.5f;
};
- /// Initialization of screen light control
- /// @param 'parent' - pointer to parent sys::Service class
- void init(sys::Service *parent);
+ /// Control screen light and keeps it's current state
+ class ScreenLightControl
+ {
+ public:
+ explicit ScreenLightControl(sys::Service *parent);
+ ~ScreenLightControl();
+
+ void processRequest(Action action, const Parameters ¶ms);
- void deinit();
+ [[nodiscard]] auto getLightState() const noexcept -> bool;
+ [[nodiscard]] auto getAutoModeState() const noexcept -> ScreenLightMode;
+ [[nodiscard]] auto getBrightnessValue() const noexcept -> bsp::eink_frontlight::BrightnessPercentage;
- void processRequest(Action action, const Parameters ¶ms);
+ private:
+ void controlTimerCallback();
+ void readoutTimerCallback();
- void controlTimerCallback();
+ void enableTimers();
+ void disableTimers();
- void readoutTimerCallback();
+ void setAutomaticModeParameters(const Parameters ¶ms);
+ void setBrightnessLevel(bsp::eink_frontlight::BrightnessPercentage brightnessPercentage);
+ void setGammaFactor(float gammaFactor);
+
+ void turnOff();
+ void turnOn();
+
+ void enableAutomaticMode();
+ void disableAutomaticMode();
+
+ template <class T> void setScreenLightSettings(const std::string &varName, T value)
+ {
+ settings->setValue(varName, utils::to_string(value));
+ }
+ void initFromSettings();
+
+ static constexpr inline auto CONTROL_TIMER_MS = 25;
+ static constexpr inline auto READOUT_TIMER_MS = 500;
+
+ std::unique_ptr<sys::Timer> controlTimer;
+ std::unique_ptr<sys::Timer> readoutTimer;
+
+ bool lightOn = false;
+ screen_light_control::ScreenLightMode automaticMode = ScreenLightMode::Manual;
+ bsp::eink_frontlight::BrightnessPercentage brightnessValue = 0.0;
+
+ std::unique_ptr<settings::Settings> settings;
+ };
-} // namespace sevm::screen_light_control
+} // namespace screen_light_control
M module-services/service-evtmgr/service-evtmgr/EVMessages.hpp => module-services/service-evtmgr/service-evtmgr/EVMessages.hpp +0 -13
@@ 5,7 5,6 @@
#include "KbdMessage.hpp"
#include "BatteryMessages.hpp"
-#include <screen-light-control/ScreenLightControl.hpp>
#include <MessageType.hpp>
#include <Service/Message.hpp>
@@ 143,16 142,4 @@ namespace sevm
bool success;
};
- class ScreenLightControlMessage : public Message
- {
- public:
- ScreenLightControlMessage(screen_light_control::Action act,
- screen_light_control::Parameters params = screen_light_control::Parameters())
- : Message(MessageType::EVMScreenLightControlMessage), action(act), parameters(params)
- {}
-
- screen_light_control::Action action;
- screen_light_control::Parameters parameters;
- };
-
} /* namespace sevm*/
M module-services/service-evtmgr/service-evtmgr/EventManager.hpp => module-services/service-evtmgr/service-evtmgr/EventManager.hpp +3 -0
@@ 11,6 11,7 @@
#include <bsp/common.hpp>
#include <bsp/keyboard/key_codes.hpp>
#include <bsp/keypad_backlight/keypad_backlight.hpp>
+#include <screen-light-control/ScreenLightControl.hpp>
#include <cstdint>
#include <memory>
@@ 40,6 41,8 @@ class EventManager : public sys::Service
// flag set when there is alarm to handle
bool alarmIsValid = false;
+ std::unique_ptr<screen_light_control::ScreenLightControl> screenLightControl;
+
public:
EventManager(const std::string &name);
~EventManager();
A module-services/service-evtmgr/service-evtmgr/ScreenLightControlMessage.hpp => module-services/service-evtmgr/service-evtmgr/ScreenLightControlMessage.hpp +55 -0
@@ 0,0 1,55 @@
+// Copyright (c) 2017-2021, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+// Copyright (c) 2017-2020, Mudita Sp. z.o.o. All rights reserved.
+// For licensing, see https://github.com/mudita/MuditaOS/LICENSE.md
+
+#pragma once
+
+#include "module-services/service-evtmgr/screen-light-control/ScreenLightControl.hpp"
+
+#include <Service/Message.hpp>
+#include <Service/Service.hpp>
+#include <utility>
+
+namespace sevm
+{
+ class ScreenLightControlMessage : public sys::DataMessage
+ {
+ public:
+ ScreenLightControlMessage() : sys::DataMessage(MessageType::ScreenLightControlAction)
+ {}
+ ScreenLightControlMessage(screen_light_control::Action act,
+ screen_light_control::Parameters params = screen_light_control::Parameters())
+ : sys::DataMessage(MessageType::ScreenLightControlAction), action(act), parameters(std::move(params))
+ {}
+
+ screen_light_control::Action action;
+ screen_light_control::Parameters parameters;
+ };
+
+ class ScreenLightControlRequestParameters : public sys::DataMessage
+ {
+ public:
+ ScreenLightControlRequestParameters() : sys::DataMessage(MessageType::ScreenLightControlParameters)
+ {}
+ };
+
+ class ScreenLightControlParametersResponse : public sys::DataMessage
+ {
+ public:
+ ScreenLightControlParametersResponse() : sys::DataMessage(MessageType::ScreenLightControlParametersResponse)
+ {}
+
+ ScreenLightControlParametersResponse(bool lightOn,
+ screen_light_control::ScreenLightMode mode,
+ screen_light_control::Parameters params)
+ : sys::DataMessage(MessageType::ScreenLightControlParametersResponse), lightOn(lightOn), mode(mode),
+ parameters(std::move(params))
+ {}
+
+ bool lightOn;
+ screen_light_control::ScreenLightMode mode;
+ screen_light_control::Parameters parameters;
+ };
+} // namespace sevm
M module-services/service-evtmgr/tests/test-ScreenLightControlFunctions.cpp => module-services/service-evtmgr/tests/test-ScreenLightControlFunctions.cpp +4 -3
@@ 6,7 6,7 @@
TEST_CASE("ScreenLightControlFunctions")
{
- using namespace sevm::screen_light_control::functions;
+ using namespace screen_light_control::functions;
constexpr auto controlTimerMS = 25;
SECTION("Ramp an hysteresis test")
@@ 14,8 14,9 @@ TEST_CASE("ScreenLightControlFunctions")
INFO("Setup");
const unsigned int testRampTime = 500;
const bsp::eink_frontlight::BrightnessPercentage testVal = 100.0f;
- BrightnessFunction functionPoints = BrightnessFunction({{0.0f, testVal}, {100.0f, 0.0f}});
- const float hysteresis = 10.0f;
+ screen_light_control::functions::BrightnessFunction functionPoints =
+ BrightnessFunction({{0.0f, testVal}, {100.0f, 0.0f}});
+ const float hysteresis = 10.0f;
setRampStep(100.0f * (static_cast<float>(controlTimerMS) / static_cast<float>(testRampTime)));
setHysteresis(hysteresis);
M module-services/service-fota/FotaUrcHandler.cpp => module-services/service-fota/FotaUrcHandler.cpp +2 -0
@@ 3,6 3,8 @@
#include "FotaUrcHandler.hpp"
+using namespace at::urc;
+
void FotaUrcHandler::Handle(Qind &urc)
{
if (urc.isFotaValid()) {
M module-services/service-fota/FotaUrcHandler.hpp => module-services/service-fota/FotaUrcHandler.hpp +11 -13
@@ 8,27 8,25 @@
#include <module-cellular/at/UrcHandler.hpp>
#include <module-cellular/at/UrcQind.hpp>
-using namespace at::urc;
-
/**
* ServiceFota helper for handling Urc messages
*/
-class FotaUrcHandler : public UrcHandler
+class FotaUrcHandler : public at::urc::UrcHandler
{
public:
FotaUrcHandler(FotaService::Service &fotaService) : fotaService(fotaService)
{}
- void Handle(Qind &urc) final;
- virtual void Handle(Clip &urc){};
- virtual void Handle(Creg &urc){};
- virtual void Handle(Cmti &urc){};
- virtual void Handle(Cusd &urc){};
- virtual void Handle(Ctze &urc){};
- virtual void Handle(Cpin &urc){};
- virtual void Handle(Qiurc &urc){};
- virtual void Handle(PoweredDown &urc){};
- virtual void Handle(UrcResponse &urc){};
+ void Handle(at::urc::Qind &urc) final;
+ virtual void Handle(at::urc::Clip &urc){};
+ virtual void Handle(at::urc::Creg &urc){};
+ virtual void Handle(at::urc::Cmti &urc){};
+ virtual void Handle(at::urc::Cusd &urc){};
+ virtual void Handle(at::urc::Ctze &urc){};
+ virtual void Handle(at::urc::Cpin &urc){};
+ virtual void Handle(at::urc::Qiurc &urc){};
+ virtual void Handle(at::urc::PoweredDown &urc){};
+ virtual void Handle(at::urc::UrcResponse &urc){};
private:
FotaService::Service &fotaService;
M module-services/service-time/service-time/CalendarTimeEvents.hpp => module-services/service-time/service-time/CalendarTimeEvents.hpp +1 -1
@@ 27,7 27,7 @@ namespace stm
{
private:
EventsRecord eventRecord;
- TimePoint startTP = TIME_POINT_INVALID;
+ calendar::TimePoint startTP = TIME_POINT_INVALID;
protected:
const std::string timerName() override
M module-services/service-time/timeEvents/CalendarTimeEvents.cpp => module-services/service-time/timeEvents/CalendarTimeEvents.cpp +4 -3
@@ 29,6 29,7 @@ namespace sys
namespace stm
{
+ using namespace std::chrono_literals;
constexpr static auto eventTimerMinSkipInterval = 100ms;
CalendarTimeEvents::CalendarTimeEvents(sys::Service *service) : TimeEvents(service)
@@ 36,8 37,8 @@ namespace stm
bool CalendarTimeEvents::sendNextEventQuery()
{
- TimePoint filterFrom = TimePointNow();
- TimePoint filterTill = filterFrom;
+ calendar::TimePoint filterFrom = TimePointNow();
+ calendar::TimePoint filterTill = filterFrom;
if (startTP != TIME_POINT_INVALID) {
filterFrom = std::min(startTP, filterFrom);
filterTill = filterFrom;
@@ 64,7 65,7 @@ namespace stm
}
eventRecord = records.at(0);
- startTP = eventRecord.date_from - minutes{eventRecord.reminder};
+ startTP = eventRecord.date_from - std::chrono::minutes{eventRecord.reminder};
auto duration = eventRecord.date_from - std::chrono::minutes{eventRecord.reminder} - TimePointNow();
if (duration.count() <= 0) {
duration = std::chrono::milliseconds(eventTimerMinSkipInterval);
M module-sys/SystemManager/SystemManager.cpp => module-sys/SystemManager/SystemManager.cpp +2 -2
@@ 116,7 116,7 @@ namespace sys
// pingPongTimerID = CreateTimer(Ticks::MsToTicks(pingInterval), true);
// ReloadTimer(pingPongTimerID);
- cpuStatisticsTimer = std::make_unique<sys::Timer>("cpuStatistics", this, timerInitInterval.count());
+ cpuStatisticsTimer = std::make_unique<sys::Timer>("cpuStatistics", this, constants::timerInitInterval.count());
cpuStatisticsTimer->connect([&](sys::Timer &) { CpuStatisticsTimerHandler(); });
cpuStatisticsTimer->start();
}
@@ 354,7 354,7 @@ namespace sys
{
if (!cpuStatisticsTimerInit) {
cpuStatisticsTimerInit = true;
- cpuStatisticsTimer->setInterval(timerPeriodInterval.count());
+ cpuStatisticsTimer->setInterval(constants::timerPeriodInterval.count());
}
cpuStatistics->Update();
M module-sys/SystemManager/SystemManager.hpp => module-sys/SystemManager/SystemManager.hpp +6 -3
@@ 26,9 26,12 @@
namespace sys
{
- using namespace std::chrono_literals;
- inline constexpr std::chrono::milliseconds timerInitInterval{30s};
- inline constexpr std::chrono::milliseconds timerPeriodInterval{100ms};
+ namespace constants
+ {
+ using namespace std::chrono_literals;
+ inline constexpr std::chrono::milliseconds timerInitInterval{30s};
+ inline constexpr std::chrono::milliseconds timerPeriodInterval{100ms};
+ } // namespace constants
enum class Code
{
M module-utils/Utils.hpp => module-utils/Utils.hpp +7 -0
@@ 122,7 122,14 @@ namespace utils
baseAsStr = "-0";
}
}
+
auto fractionalPart = static_cast<unsigned long int>(roundl(frac));
+ auto fractionalPartLength = std::to_string(fractionalPart).length();
+ if (fractionalPartLength > precision) {
+ base += 1;
+ baseAsStr = std::to_string(base);
+ fractionalPart = 0;
+ }
if (fractionalPart == 0) {
if (baseAsStr == "-0") {
return "0";
M module-utils/ical/ParserICS.cpp => module-utils/ical/ParserICS.cpp +8 -5
@@ 446,7 446,7 @@ auto Event::timeStringFrom(const std::string &icalTime) const -> std::string
getSecondsFromIcalTime(icalTime);
}
-auto Event::TimePointFromIcalDate(const std::string &icalDateTime) const -> TimePoint
+auto Event::TimePointFromIcalDate(const std::string &icalDateTime) const -> calendar::TimePoint
{
std::string icalDate(getDateFromIcalFormat(icalDateTime));
std::string icalTime(getTimeFromIcalFormat(icalDateTime));
@@ 459,7 459,7 @@ auto Event::TimePointFromIcalDate(const std::string &icalDateTime) const -> Time
return TimePointFromString(dateTime.c_str());
}
-auto Event::TimePointToIcalDate(const TimePoint &tp) const -> std::string
+auto Event::TimePointToIcalDate(const calendar::TimePoint &tp) const -> std::string
{
constexpr uint32_t bufferLimit = 16;
auto time = TimePointToTimeT(tp);
@@ 541,7 541,10 @@ auto Event::validateUID(const std::string &UID) -> bool
return validateDT(DTimestamp);
}
-Event::Event(const std::string &summary, const TimePoint from, TimePoint till, const std::string &uid)
+Event::Event(const std::string &summary,
+ const calendar::TimePoint from,
+ calendar::TimePoint till,
+ const std::string &uid)
{
if (summary.empty()) {
isValid = false;
@@ 595,12 598,12 @@ auto Event::getSummary() const -> std::string
return summary;
}
-auto Event::getDTStartTimePoint() const -> TimePoint
+auto Event::getDTStartTimePoint() const -> calendar::TimePoint
{
return dtstart;
}
-auto Event::getDTEndTimePoint() const -> TimePoint
+auto Event::getDTEndTimePoint() const -> calendar::TimePoint
{
return dtend;
}
M module-utils/ical/ParserICS.hpp => module-utils/ical/ParserICS.hpp +7 -7
@@ 91,8 91,8 @@ class Event
{
std::string uid;
std::string summary;
- TimePoint dtstart;
- TimePoint dtend;
+ calendar::TimePoint dtstart;
+ calendar::TimePoint dtend;
auto isDate(const std::string &dt) -> bool;
auto isTime(const std::string &dt) -> bool;
@@ 112,13 112,13 @@ class Event
[[nodiscard]] auto dateStringFrom(const std::string &icalDate) const -> std::string;
[[nodiscard]] auto timeStringFrom(const std::string &icalTime) const -> std::string;
- [[nodiscard]] auto TimePointFromIcalDate(const std::string &icalDateTime) const -> TimePoint;
- [[nodiscard]] auto TimePointToIcalDate(const TimePoint &tp) const -> std::string;
+ [[nodiscard]] auto TimePointFromIcalDate(const std::string &icalDateTime) const -> calendar::TimePoint;
+ [[nodiscard]] auto TimePointToIcalDate(const calendar::TimePoint &tp) const -> std::string;
public:
bool isValid = true;
Event() = default;
- Event(const std::string &summary, TimePoint from, TimePoint till, const std::string &uid);
+ Event(const std::string &summary, calendar::TimePoint from, calendar::TimePoint till, const std::string &uid);
void setUID(const std::string &property);
void setSummary(const std::string &property);
@@ 127,8 127,8 @@ class Event
[[nodiscard]] auto getUID() const -> std::string;
[[nodiscard]] auto getSummary() const -> std::string;
- [[nodiscard]] auto getDTStartTimePoint() const -> TimePoint;
- [[nodiscard]] auto getDTEndTimePoint() const -> TimePoint;
+ [[nodiscard]] auto getDTStartTimePoint() const -> calendar::TimePoint;
+ [[nodiscard]] auto getDTEndTimePoint() const -> calendar::TimePoint;
[[nodiscard]] auto getDTStartString() const -> std::string;
[[nodiscard]] auto getDTEndString() const -> std::string;
M module-utils/time/TimeRangeParser.cpp => module-utils/time/TimeRangeParser.cpp +2 -2
@@ 19,8 19,8 @@ namespace utils::time
return utils::localize.get(utils::time::Locale::getPM());
}
- std::string TimeRangeParser::getCalendarTimeString(TimePoint startDate,
- TimePoint endDate,
+ std::string TimeRangeParser::getCalendarTimeString(calendar::TimePoint startDate,
+ calendar::TimePoint endDate,
Version version,
bool isMode24H)
{
M module-utils/time/TimeRangeParser.hpp => module-utils/time/TimeRangeParser.hpp +2 -2
@@ 20,8 20,8 @@ namespace utils::time
std::string AMPMtoString(bool isAm);
public:
- std::string getCalendarTimeString(TimePoint startDate,
- TimePoint endDate,
+ std::string getCalendarTimeString(calendar::TimePoint startDate,
+ calendar::TimePoint endDate,
Version version = Version::normal,
bool isMode24H = false);
};
M module-utils/time/time_conversion.cpp => module-utils/time/time_conversion.cpp +1 -1
@@ 277,7 277,7 @@ namespace utils::time
}
else {
return Timestamp::str(
- Locale::format(Locale::FormatTime12H)); // @TODO: M.G. FormatLocaleTime which actually works
+ Locale::format(Locale::FormatTime12HShort)); // @TODO: M.G. FormatLocaleTime which actually works
}
}
M module-utils/time/time_locale.hpp => module-utils/time/time_locale.hpp +3 -1
@@ 21,7 21,7 @@ namespace utils
{
static const int num_days = 7;
static const int num_monts = 12;
- static const int num_formatters = 4;
+ static const int num_formatters = 5;
// imo it would be nicer to have datetime locales in different json with thiny bit nicer and more effective
// getters
const std::array<std::string, num_days> daysShort = {
@@ 50,6 50,7 @@ namespace utils
const std::array<std::string, num_formatters> time_formats{
"locale_12hour_min",
+ "locale_12hour_min_short",
"locale_24hour_min",
"locale_date_full",
"locale_date_short",
@@ 90,6 91,7 @@ namespace utils
enum TimeFormat
{
FormatTime12H = 0, // H:M in 12h format
+ FormatTime12HShort, // H:M in 12h format, am/pm excluded
FormatTime24H, // H:M in 24h format
FormatLocaleDateFull, // format locale specified format
FormatLocaleDateShort, // format locale specified format
M source/MessageType.hpp => source/MessageType.hpp +6 -3
@@ 177,8 177,6 @@ enum class MessageType
EVMTorchStateMessage,
// Keypad backlight control messages
EVMKeypadBacklightMessage,
- // Screen frontlight control messages
- EVMScreenLightControlMessage,
// cellular messages
EVMGetBoard,
@@ 238,7 236,12 @@ enum class MessageType
AntennaLockNotification,
Settings,
FileContentModified,
- FileIndexer
+ FileIndexer,
+
+ // Screen frontlight control messages
+ ScreenLightControlAction,
+ ScreenLightControlParameters,
+ ScreenLightControlParametersResponse,
};
#endif /* SOURCE_MESSAGETYPE_HPP_ */
M tools/check_commit_messages.py => tools/check_commit_messages.py +1 -1
@@ 33,7 33,7 @@ def validate_commit(commit):
empty_line = lines[1]
body = ''.join(lines[2:]).strip()
- subject_format = r'^\[\w+-\d+\] .+[^.]$'
+ subject_format = r'^\[EGD-\d+\] [A-Z].+[^.]$'
if not re.match(subject_format, subject):
errors.append(f'[{commit.hexsha}] invalid subject "{subject}", should match format "{subject_format}"')
A tools/clang-tidy.cmake => tools/clang-tidy.cmake +19 -0
@@ 0,0 1,19 @@
+find_program(RUN_CLANG_TIDY_COMMAND NAMES run-clang-tidy)
+if (NOT RUN_CLANG_TIDY_COMMAND)
+ message(WARNING "run-clang-tidy can not be found.")
+ return()
+endif()
+
+if (NOT CMAKE_EXPORT_COMPILE_COMMANDS)
+ message(WARNING "Unable to run clang-tidy without the compile commands database.")
+ return()
+endif()
+
+set(STATIC_ANALYSIS_OUTPUT_DIR "StaticAnalysis")
+
+string(TIMESTAMP CURRENT_TIME)
+set(CLANG_TIDY_OUTPUL_FILE "clang-tidy_${CURRENT_TIME}")
+
+add_custom_target(clang-tidy
+ COMMAND ${CMAKE_COMMAND} -E make_directory ${STATIC_ANALYSIS_OUTPUT_DIR}
+ COMMAND ${RUN_CLANG_TIDY_COMMAND} -header-filter='.*' -p ${CMAKE_BINARY_DIR} > "${STATIC_ANALYSIS_OUTPUT_DIR}/${CLANG_TIDY_OUTPUL_FILE}")
M tools/download_asset.py => tools/download_asset.py +3 -2
@@ 52,7 52,7 @@ class Getter(object):
try:
gitConfigReader = self.gitRepo.config_reader()
self.apitoken = gitConfigReader.get_value("user", "apitoken")
- except git.exc.NoOptionError as error:
+ except:
pass
def getGHLogin(self, args=None):
@@ 63,7 63,7 @@ class Getter(object):
try:
gitConfigReader = self.gitRepo.config_reader()
self.ghLogin = gitConfigReader.get_value("user", "githublogin")
- except git.exc.NoOptionError as error:
+ except:
pass
def findWorkDir(self):
@@ 117,6 117,7 @@ class Getter(object):
break
if release is None:
print("No release with tag:", args.tag)
+ print("release:", release['tag_name'])
assets = release['assets']
self.downloadAsset(assets[0])