From 60abbf0639d14334a27569da7cec71c447a2ab92 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jean-Fran=C3=A7ois=20Milants?= Date: Sun, 2 Oct 2022 12:27:10 +0200 Subject: [PATCH] Add doc about external resources. --- README.md | 1 + doc/ExternalResources.md | 70 ++++++++++++++++++ doc/gettingStarted/itd-external-resources.png | Bin 0 -> 11869 bytes doc/gettingStarted/updating-software.md | 32 ++++++++ 4 files changed, 103 insertions(+) create mode 100644 doc/ExternalResources.md create mode 100644 doc/gettingStarted/itd-external-resources.png diff --git a/README.md b/README.md index a3d2229b..6fd41586 100644 --- a/README.md +++ b/README.md @@ -28,6 +28,7 @@ Fast open-source firmware for the [PineTime smartwatch](https://www.pine64.org/p - [Generate the fonts and symbols](src/displayapp/fonts/README.md) - [Tips on designing an app UI](doc/ui_guidelines.md) - [Bootloader, OTA and DFU](bootloader/README.md) +- [External resources](doc/ExternalResources.md) - [Versioning](doc/versioning.md) - [Project branches](doc/branches.md) - [Files included in the release notes](doc/filesInReleaseNotes.md) diff --git a/doc/ExternalResources.md b/doc/ExternalResources.md new file mode 100644 index 00000000..85319f6f --- /dev/null +++ b/doc/ExternalResources.md @@ -0,0 +1,70 @@ +# External resources +Since InfiniTime 1.11 apps and watchfaces can benefit from the external flash memory to store images and fonts. +This external memory is a lot bigger (4MB) than the internal memory that contains the firmware (512KB). + +This page describes how the resources are integrated in InfiniTime from a developer perspective. [This page](gettingStarted/updating-software.md) explains how to install and update the external resources using companion apps. + +## Resources generation + +Resources are generated at build time via the [CMake target `Generate Resources`](https://github.com/InfiniTimeOrg/InfiniTime/blob/develop/src/resources/CMakeLists.txt#L19). +It runs 3 Python scripts that respectively convert the fonts to binary format, convert the images to binary format and package everything in a .zip file. + +The resulting file `infinitime-resources-x.y.z.zip` contains the images and fonts converted in binary `.bin` files and a JSON file `resources.json`. + +Companion apps use this file to upload the files to the watch. + +``` +{ + "resources": [ + { + "filename": "lv_font_dots_40.bin", + "path": "/fonts/lv_font_dots_40.bin" + } + ], + "obsolete_files": [ + { + "path": "/example-of-obsolete-file.bin", + "since": "1.11.0" + } + ] +} +``` + +The resource JSON file describes an array of resources and an array of obsolete files : + +- `resources` : a resource is a file that must be flashed to the watch + - `filename`: name of the resources in the zip file. + - `path` : file path and name where the file must be flashed in the watch FS. + +- `obsolete_files` : files that are not needed anymore in the memory of the watch that can be deleted during the update procedure. + - `path` : path of the file in the watch FS + - `since` : version of InfiniTime that made this file obsolete. + +## Resources update procedure + +The update procedure is based on the [BLE FS API](BLEFS.md). The companion app simply write the binary files to the watch FS using information from the file `resources.json`. + +## Working with external resources in the code + +Load a picture from the external resources: + +``` +lv_obj_t* logo = lv_img_create(lv_scr_act(), nullptr); +lv_img_set_src(logo, "F:/images/logo.bin"); +``` + +Load a font from the external resources: you first need to check that the file actually exists. LVGL will crash when trying to open a font that doesn't exist. + +``` +lv_font_t* font_teko = nullptr; +if (filesystem.FileOpen(&f, "/fonts/font.bin", LFS_O_RDONLY) >= 0) { + filesystem.FileClose(&f); + font_teko = lv_font_load("F:/fonts/font.bin"); +} + +if(font != nullptr) { + lv_obj_set_style_local_text_font(label, LV_LABEL_PART_MAIN, LV_STATE_DEFAULT, font); +} + +``` + diff --git a/doc/gettingStarted/itd-external-resources.png b/doc/gettingStarted/itd-external-resources.png new file mode 100644 index 0000000000000000000000000000000000000000..b3ff99be20c0c051c8c677225cc0edc6ebf87a97 GIT binary patch literal 11869 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 VW~hQ!5VBqzP?CEqTP= 1.0 by following this si - Open settings by tapping the cogwheel on the bottom right - Swipe up until you find an entry named **Firmware** and tap on it - If the firmware is not validated yet, you can either validate the running firmware, or reset and revert to the previous firmware version + +# Updating resources + +Since InfiniTime 1.11 apps and watchfaces can take benefit of the external flash memory to store their pictures and fonts. +This external memory is a lot bigger (4MB) than the internal memory where the firmware is flashed (512KB). +Since those resources are not part of the firmware, they need to be flashed and updated separately. + +Resources are packaged into a single .zip file named `infinitime-resources-x.y.z.zip` (where `x`, `y` and `z` are the version numbers of InfiniTime). +You can use the companion app of your choice to flash the resources. + +**Note : at the time of writing this page, [Amazfish](https://github.com/piggz/harbour-amazfish) and [ITD](https://gitea.arsenm.dev/Arsen6331/itd) have already integrated this functionality. Other companion apps will hopefully implement it soon!* + +## Amazfish +Use the `Download file` functionality of Amazfish. + +![Update resources with Amazfish - Download file](amazfish-external-resources-1.png) + +Amazfish automatically detects the file type (firmware or resources) and apply the corresponding flash procedure when you hit the button **Send file**. + +![Update resources with Amazfish](amazfish-external-resources-2.png) + +## ITD + +Run `itctl` with the `res` command: + +``` +itctl res load infinitime-resources-1.10.0.zip +``` + +Example: + +![Update resources using itctl](itd-external-resources.png)