diff --git a/.devcontainer/Dockerfile b/.devcontainer/Dockerfile deleted file mode 100644 index 797e089..0000000 --- a/.devcontainer/Dockerfile +++ /dev/null @@ -1,159 +0,0 @@ -# Copy paste of https://github.com/espressif/esp-idf/blob/master/tools/docker/Dockerfile -# but with ubuntu image downgraded. -# You must download https://github.com/espressif/esp-idf/blob/master/tools/docker/entrypoint.sh -# and place it in the .devcontainer directory. -#FROM ubuntu:24.04 -FROM ubuntu:22.04 - -ARG DEBIAN_FRONTEND=noninteractive - -RUN : \ - && apt-get update \ - && apt-get install -y \ - apt-utils \ - bison \ - bzip2 \ - ca-certificates \ - ccache \ - check \ - curl \ - flex \ - git \ - git-lfs \ - gperf \ - lcov \ - libbsd-dev \ - libffi-dev \ - libglib2.0-0 \ - libncurses-dev \ - libpixman-1-0 \ - libsdl2-2.0-0 \ - libslirp0 \ - libusb-1.0-0-dev \ - make \ - ninja-build \ - python3 \ - python3-venv \ - ruby \ - unzip \ - wget \ - xz-utils \ - zip \ - && apt-get autoremove -y \ - && rm -rf /var/lib/apt/lists/* \ - && update-alternatives --install /usr/bin/python python /usr/bin/python3 10 \ - && : - -# To build the image for a branch or a tag of IDF, pass --build-arg IDF_CLONE_BRANCH_OR_TAG=name. -# To build the image with a specific commit ID of IDF, pass --build-arg IDF_CHECKOUT_REF=commit-id. -# It is possible to combine both, e.g.: -# IDF_CLONE_BRANCH_OR_TAG=release/vX.Y -# IDF_CHECKOUT_REF=. -# Use IDF_CLONE_SHALLOW=1 to perform shallow clone (i.e. --depth=1 --shallow-submodules) -# Use IDF_CLONE_SHALLOW_DEPTH=X to define the depth if IDF_CLONE_SHALLOW is used (i.e. --depth=X) -# Use IDF_INSTALL_TARGETS to install tools only for selected chip targets (CSV) - -ARG IDF_CLONE_URL=https://github.com/espressif/esp-idf.git -ARG IDF_CLONE_BRANCH_OR_TAG=master -ARG IDF_CHECKOUT_REF= -ARG IDF_CLONE_SHALLOW= -ARG IDF_CLONE_SHALLOW_DEPTH=1 -ARG IDF_INSTALL_TARGETS=all - -ENV IDF_PATH=/opt/esp/idf -ENV IDF_TOOLS_PATH=/opt/esp - -# install build essential needed for linux target apps, which is a preview target so it is installed with "all" only -RUN if [ "$IDF_INSTALL_TARGETS" = "all" ]; then \ - apt-get update \ - && apt-get install -y build-essential \ - && apt-get autoremove -y \ - && rm -rf /var/lib/apt/lists/* ; \ - fi - -RUN echo IDF_CHECKOUT_REF=$IDF_CHECKOUT_REF IDF_CLONE_BRANCH_OR_TAG=$IDF_CLONE_BRANCH_OR_TAG && \ - git clone --recursive \ - ${IDF_CLONE_SHALLOW:+--depth=${IDF_CLONE_SHALLOW_DEPTH} --shallow-submodules} \ - ${IDF_CLONE_BRANCH_OR_TAG:+-b $IDF_CLONE_BRANCH_OR_TAG} \ - $IDF_CLONE_URL $IDF_PATH && \ - git config --system --add safe.directory $IDF_PATH && \ - if [ -n "$IDF_CHECKOUT_REF" ]; then \ - cd $IDF_PATH && \ - if [ -n "$IDF_CLONE_SHALLOW" ]; then \ - git fetch origin --depth=${IDF_CLONE_SHALLOW_DEPTH} --recurse-submodules ${IDF_CHECKOUT_REF}; \ - fi && \ - git checkout $IDF_CHECKOUT_REF && \ - git submodule update --init --recursive; \ - fi - -# Install all the required tools -RUN : \ - && update-ca-certificates --fresh \ - && $IDF_PATH/tools/idf_tools.py --non-interactive install required --targets=${IDF_INSTALL_TARGETS} \ - && $IDF_PATH/tools/idf_tools.py --non-interactive install qemu* --targets=${IDF_INSTALL_TARGETS} \ - && $IDF_PATH/tools/idf_tools.py --non-interactive install cmake \ - && $IDF_PATH/tools/idf_tools.py --non-interactive install-python-env \ - && rm -rf $IDF_TOOLS_PATH/dist \ - && : - -# Add get_idf as alias -RUN echo 'alias get_idf=". /opt/esp/idf/export.sh"' >> /root/.bashrc - -# The constraint file has been downloaded and the right Python package versions installed. No need to check and -# download this at every invocation of the container. -ENV IDF_PYTHON_CHECK_CONSTRAINTS=no - -# Ccache is installed, enable it by default -ENV IDF_CCACHE_ENABLE=1 - -COPY entrypoint.sh /opt/esp/entrypoint.sh -RUN chmod +x /opt/esp/entrypoint.sh - -#Original file starts here -#FROM espressif/idf - -#ARG DEBIAN_FRONTEND=nointeractive -ARG CONTAINER_USER=esp -ARG USER_UID=1050 -ARG USER_GID=$USER_UID - -RUN apt-get update \ - && apt install -y -q \ - cmake \ - git \ - libglib2.0-0 \ - libnuma1 \ - libpixman-1-0 \ - && rm -rf /var/lib/apt/lists/* - -# QEMU -ENV QEMU_REL=esp_develop_8.2.0_20240122 -ENV QEMU_SHA256=e7c72ef5705ad1444d391711088c8717fc89f42e9bf6d1487f9c2a326b8cfa83 -ENV QEMU_DIST=qemu-xtensa-softmmu-${QEMU_REL}-x86_64-linux-gnu.tar.xz -ENV QEMU_URL=https://github.com/espressif/qemu/releases/download/esp-develop-8.2.0-20240122/${QEMU_DIST} - -ENV LC_ALL=C.UTF-8 -ENV LANG=C.UTF-8 - -RUN wget --no-verbose ${QEMU_URL} \ - && echo "${QEMU_SHA256} *${QEMU_DIST}" | sha256sum --check --strict - \ - && tar -xf $QEMU_DIST -C /opt \ - && rm ${QEMU_DIST} - -ENV PATH=/opt/qemu/bin:${PATH} - -RUN groupadd --gid $USER_GID $CONTAINER_USER \ - && adduser --uid $USER_UID --gid $USER_GID --disabled-password --gecos "" ${CONTAINER_USER} \ - && usermod -a -G root $CONTAINER_USER && usermod -a -G dialout $CONTAINER_USER - -RUN chmod -R 775 /opt/esp/python_env/ - -USER ${CONTAINER_USER} -ENV USER=${CONTAINER_USER} -WORKDIR /home/${CONTAINER_USER} - -RUN echo "source /opt/esp/idf/export.sh > /dev/null 2>&1" >> ~/.bashrc - -ENTRYPOINT [ "/opt/esp/entrypoint.sh" ] - -CMD ["/bin/bash", "-c"] \ No newline at end of file diff --git a/.devcontainer/devcontainer.json b/.devcontainer/devcontainer.json deleted file mode 100644 index 2d88163..0000000 --- a/.devcontainer/devcontainer.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "name": "ESP-IDF QEMU", - "build": { - "dockerfile": "Dockerfile" - }, - "customizations": { - "vscode": { - "settings": { - "terminal.integrated.defaultProfile.linux": "bash", - "idf.espIdfPath": "/opt/esp/idf", - "idf.toolsPath": "/opt/esp", - "idf.gitPath": "/usr/bin/git" - }, - "extensions": [ - "espressif.esp-idf-extension", - "espressif.esp-idf-web" - ] - }, - "codespaces": { - "settings": { - "terminal.integrated.defaultProfile.linux": "bash", - "idf.espIdfPath": "/opt/esp/idf", - "idf.toolsPath": "/opt/esp", - "idf.gitPath": "/usr/bin/git" - }, - "extensions": [ - "espressif.esp-idf-extension", - "espressif.esp-idf-web" - ] - } - }, - "runArgs": ["--privileged"] -} \ No newline at end of file diff --git a/.devcontainer/entrypoint.sh b/.devcontainer/entrypoint.sh deleted file mode 100644 index 513b3ba..0000000 --- a/.devcontainer/entrypoint.sh +++ /dev/null @@ -1,20 +0,0 @@ -#!/usr/bin/env bash -set -e - -# IDF_GIT_SAFE_DIR has the same format as system PATH environment variable. -# All path specified in IDF_GIT_SAFE_DIR will be added to user's -# global git config as safe.directory paths. For more information -# see git-config manual page. -if [ -n "${IDF_GIT_SAFE_DIR+x}" ] -then - echo "Adding following directories into git's safe.directory" - echo "$IDF_GIT_SAFE_DIR" | tr ':' '\n' | while read -r dir - do - git config --global --add safe.directory "$dir" - echo " $dir" - done -fi - -. $IDF_PATH/export.sh - -exec "$@" diff --git a/.vscode/c_cpp_properties.json b/.vscode/c_cpp_properties.json index 2c42bb8..25ab9c7 100644 --- a/.vscode/c_cpp_properties.json +++ b/.vscode/c_cpp_properties.json @@ -2,7 +2,7 @@ "configurations": [ { "name": "ESP-IDF", - "compilerPath": "${config:idf.toolsPathWin}\\tools\\xtensa-esp-elf\\esp-13.2.0_20230928\\xtensa-esp-elf\\bin\\xtensa-esp32s3-elf-gcc.exe", + "compilerPath": "${config:idf.toolsPath}/tools/xtensa-esp-elf/esp-13.2.0_20240530/xtensa-esp-elf/bin/xtensa-esp32s3-elf-gcc", "compileCommands": "${config:idf.buildPath}/compile_commands.json", "includePath": [ "${config:idf.espIdfPath}/components/**", @@ -16,8 +16,9 @@ "${workspaceFolder}" ], "limitSymbolsToIncludedHeaders": true - } + }, + "configurationProvider": "ms-vscode.cmake-tools" } ], "version": 4 -} +} \ No newline at end of file diff --git a/.vscode/launch.json b/.vscode/launch.json index 2511a38..56481e4 100644 --- a/.vscode/launch.json +++ b/.vscode/launch.json @@ -1,6 +1,7 @@ { "version": "0.2.0", "configurations": [ + { "type": "gdbtarget", "request": "attach", @@ -10,6 +11,27 @@ "type": "espidf", "name": "Launch", "request": "launch" - } + }, + { + "name": "Debug LVGL demo with gdb", + "type": "cppdbg", + "request": "launch", + "program": "${workspaceFolder}/bin/main", + "args": [], + "cwd": "${workspaceFolder}", + "stopAtEntry": false, + "linux": { + "MIMode": "gdb", + "miDebuggerPath": "/usr/bin/gdb" + }, + "osx": { + "MIMode": "lldb" + }, + "windows": { + "MIMode": "gdb", + "miDebuggerPath": "C:\\MinGw\\bin\\gdb.exe" + } + }, + ] } \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json index 10b3089..58540d2 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,18 +1,91 @@ { - "idf.adapterTargetName": "esp32s3", - "idf.flashType": "UART", - "idf.portWin": "COM11", - "files.associations": { - "wifi.h": "c", - "esp_log.h": "c", - "esp_wifi.h": "c", - "esp_lvgl_port.h": "c", - "mqtt.h": "c", - "stdio.h": "c", - "locale.h": "c", - "obtain_time.h": "c", - "i2c.h": "c", - "lv_global.h": "c", - "cstdint": "c" - } -} \ No newline at end of file + "C_Cpp.intelliSenseEngine": "default", + "idf.espIdfPath": "/home/marc/esp/v5.3.1/esp-idf", + "idf.pythonBinPath": "/home/marc/.espressif/python_env/idf5.3_py3.10_env/bin/python", + "idf.toolsPath": "/home/marc/.espressif", + "idf.customExtraPaths": "/home/marc/.espressif/tools/xtensa-esp-elf-gdb/14.2_20240403/xtensa-esp-elf-gdb/bin:/home/marc/.espressif/tools/riscv32-esp-elf-gdb/14.2_20240403/riscv32-esp-elf-gdb/bin:/home/marc/.espressif/tools/xtensa-esp-elf/esp-13.2.0_20240530/xtensa-esp-elf/bin:/home/marc/.espressif/tools/riscv32-esp-elf/esp-13.2.0_20240530/riscv32-esp-elf/bin:/home/marc/.espressif/tools/esp32ulp-elf/2.38_20240113/esp32ulp-elf/bin:/home/marc/.espressif/tools/cmake/3.24.0/bin:/home/marc/.espressif/tools/openocd-esp32/v0.12.0-esp32-20240318/openocd-esp32/bin:/home/marc/.espressif/tools/ninja/1.11.1:/home/marc/.espressif/tools/esp-rom-elfs/20240305", + "idf.customExtraVars": { + "OPENOCD_SCRIPTS": "/home/marc/.espressif/tools/openocd-esp32/v0.12.0-esp32-20240318/openocd-esp32/share/openocd/scripts", + "ESP_ROM_ELF_DIR": "/home/marc/.espressif/tools/esp-rom-elfs/20240305/" + }, + "idf.gitPath": "git", + "idf.adapterTargetName": "esp32s3", + "idf.openOcdConfigs": [ + "board/esp32s3-builtin.cfg" + ], + "idf.flashType": "UART", + "idf.port": "/dev/ttyUSB0", + "cmake.additionalCompilerSearchDirs": [ + "/home/marc/.espressif/tools/xtensa-esp-elf/esp-13.2.0_20240530/xtensa-esp-elf/bin/" + ], + "files.associations": { + "array": "cpp", + "atomic": "cpp", + "bit": "cpp", + "*.tcc": "cpp", + "bitset": "cpp", + "cctype": "cpp", + "charconv": "cpp", + "chrono": "cpp", + "clocale": "cpp", + "cmath": "cpp", + "compare": "cpp", + "concepts": "cpp", + "condition_variable": "cpp", + "cstdarg": "cpp", + "cstddef": "cpp", + "cstdint": "cpp", + "cstdio": "cpp", + "cstdlib": "cpp", + "cstring": "cpp", + "ctime": "cpp", + "cwchar": "cpp", + "cwctype": "cpp", + "deque": "cpp", + "list": "cpp", + "map": "cpp", + "string": "cpp", + "unordered_map": "cpp", + "vector": "cpp", + "exception": "cpp", + "algorithm": "cpp", + "functional": "cpp", + "iterator": "cpp", + "memory": "cpp", + "memory_resource": "cpp", + "numeric": "cpp", + "optional": "cpp", + "random": "cpp", + "ratio": "cpp", + "regex": "cpp", + "string_view": "cpp", + "system_error": "cpp", + "tuple": "cpp", + "type_traits": "cpp", + "utility": "cpp", + "format": "cpp", + "fstream": "cpp", + "future": "cpp", + "initializer_list": "cpp", + "iomanip": "cpp", + "iosfwd": "cpp", + "iostream": "cpp", + "istream": "cpp", + "limits": "cpp", + "mutex": "cpp", + "new": "cpp", + "numbers": "cpp", + "ostream": "cpp", + "semaphore": "cpp", + "span": "cpp", + "sstream": "cpp", + "stdexcept": "cpp", + "stop_token": "cpp", + "streambuf": "cpp", + "thread": "cpp", + "cinttypes": "cpp", + "typeinfo": "cpp", + "variant": "cpp" + }, + "idf.pythonInstallPath": "/usr/bin/python3" +} diff --git a/.vscode/tasks.json b/.vscode/tasks.json new file mode 100644 index 0000000..1dc7915 --- /dev/null +++ b/.vscode/tasks.json @@ -0,0 +1,259 @@ +{ + "version": "2.0.0", + "tasks": [ + { + "label": "Build - Build project", + "type": "shell", + "command": "${config:idf.pythonBinPath} ${config:idf.espIdfPath}/tools/idf.py build", + "windows": { + "command": "${config:idf.pythonBinPathWin} ${config:idf.espIdfPathWin}\\tools\\idf.py build", + "options": { + "env": { + "PATH": "${env:PATH};${config:idf.customExtraPaths}" + } + } + }, + "options": { + "env": { + "PATH": "${env:PATH}:${config:idf.customExtraPaths}" + } + }, + "problemMatcher": [ + { + "owner": "cpp", + "fileLocation": [ + "autoDetect", + "${workspaceFolder}" + ], + "pattern": { + "regexp": "^(.*?):(\\d+):(\\d*):?\\s+(?:fatal\\s+)?(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + } + ], + "group": { + "kind": "build", + "isDefault": true + } + }, + { + "label": "Set ESP-IDF Target", + "type": "shell", + "command": "${command:espIdf.setTarget}", + "problemMatcher": { + "owner": "cpp", + "fileLocation": [ + "autoDetect", + "${workspaceFolder}" + ], + "pattern": { + "regexp": "^(.*?):(\\d+):(\\d*):?\\s+(?:fatal\\s+)?(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + } + }, + { + "label": "Clean - Clean the project", + "type": "shell", + "command": "${config:idf.pythonBinPath} ${config:idf.espIdfPath}/tools/idf.py fullclean", + "windows": { + "command": "${config:idf.pythonBinPathWin} ${config:idf.espIdfPathWin}\\tools\\idf.py fullclean", + "options": { + "env": { + "PATH": "${env:PATH};${config:idf.customExtraPaths}" + } + } + }, + "options": { + "env": { + "PATH": "${env:PATH}:${config:idf.customExtraPaths}" + } + }, + "problemMatcher": [ + { + "owner": "cpp", + "fileLocation": [ + "autoDetect", + "${workspaceFolder}" + ], + "pattern": { + "regexp": "^(.*?):(\\d+):(\\d*):?\\s+(?:fatal\\s+)?(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + } + ] + }, + { + "label": "Flash - Flash the device", + "type": "shell", + "command": "${config:idf.pythonBinPath} ${config:idf.espIdfPath}/tools/idf.py -p ${config:idf.port} -b ${config:idf.flashBaudRate} flash", + "windows": { + "command": "${config:idf.pythonBinPathWin} ${config:idf.espIdfPathWin}\\tools\\idf.py flash -p ${config:idf.portWin} -b ${config:idf.flashBaudRate}", + "options": { + "env": { + "PATH": "${env:PATH};${config:idf.customExtraPaths}" + } + } + }, + "options": { + "env": { + "PATH": "${env:PATH}:${config:idf.customExtraPaths}" + } + }, + "problemMatcher": [ + { + "owner": "cpp", + "fileLocation": [ + "autoDetect", + "${workspaceFolder}" + ], + "pattern": { + "regexp": "^(.*?):(\\d+):(\\d*):?\\s+(?:fatal\\s+)?(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + } + ] + }, + { + "label": "Monitor: Start the monitor", + "type": "shell", + "command": "${config:idf.pythonBinPath} ${config:idf.espIdfPath}/tools/idf.py -p ${config:idf.port} monitor", + "windows": { + "command": "${config:idf.pythonBinPathWin} ${config:idf.espIdfPathWin}\\tools\\idf.py -p ${config:idf.portWin} monitor", + "options": { + "env": { + "PATH": "${env:PATH};${config:idf.customExtraPaths}" + } + } + }, + "options": { + "env": { + "PATH": "${env:PATH}:${config:idf.customExtraPaths}" + } + }, + "problemMatcher": [ + { + "owner": "cpp", + "fileLocation": [ + "autoDetect", + "${workspaceFolder}" + ], + "pattern": { + "regexp": "^(.*?):(\\d+):(\\d*):?\\s+(?:fatal\\s+)?(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + } + ], + "dependsOn": "Flash - Flash the device" + }, + { + "label": "OpenOCD: Start openOCD", + "type": "shell", + "presentation": { + "echo": true, + "reveal": "never", + "focus": false, + "panel": "new" + }, + "command": "openocd -s ${command:espIdf.getOpenOcdScriptValue} ${command:espIdf.getOpenOcdConfigs}", + "windows": { + "command": "openocd.exe -s ${command:espIdf.getOpenOcdScriptValue} ${command:espIdf.getOpenOcdConfigs}", + "options": { + "env": { + "PATH": "${env:PATH};${config:idf.customExtraPaths}" + } + } + }, + "options": { + "env": { + "PATH": "${env:PATH}:${config:idf.customExtraPaths}" + } + }, + "problemMatcher": { + "owner": "cpp", + "fileLocation": [ + "autoDetect", + "${workspaceFolder}" + ], + "pattern": { + "regexp": "^(.*?):(\\d+):(\\d*):?\\s+(?:fatal\\s+)?(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "column": 3, + "severity": 4, + "message": 5 + } + } + }, + { + "label": "adapter", + "type": "shell", + "command": "${config:idf.pythonBinPath}", + "isBackground": true, + "options": { + "env": { + "PATH": "${env:PATH}:${config:idf.customExtraPaths}", + "PYTHONPATH": "${command:espIdf.getExtensionPath}/esp_debug_adapter/debug_adapter" + } + }, + "problemMatcher": { + "background": { + "beginsPattern": "\bDEBUG_ADAPTER_STARTED\b", + "endsPattern": "DEBUG_ADAPTER_READY2CONNECT", + "activeOnStart": true + }, + "pattern": { + "regexp": "(\\d+)-(\\d+)-(\\d+)\\s(\\d+):(\\d+):(\\d+),(\\d+)\\s-(.+)\\s(ERROR)", + "file": 8, + "line": 2, + "column": 3, + "severity": 4, + "message": 9 + } + }, + "args": [ + "${command:espIdf.getExtensionPath}/esp_debug_adapter/debug_adapter_main.py", + "-e", + "${workspaceFolder}/build/${command:espIdf.getProjectName}.elf", + "-s", + "$OPENOCD_SCRIPTS", + "-dn", + "esp32", + "-om", + "connect_to_instance", + "-t", + "xtensa-esp32-elf-" + + ], + "windows": { + "command": "${config:idf.pythonBinPathWin}", + "options": { + "env": { + "PATH": "${env:PATH};${config:idf.customExtraPaths}", + "PYTHONPATH": "${command:espIdf.getExtensionPath}/esp_debug_adapter/debug_adapter" + } + } + } + } + ] +} \ No newline at end of file diff --git a/.vscode__/c_cpp_properties.json b/.vscode__/c_cpp_properties.json deleted file mode 100644 index 042e129..0000000 --- a/.vscode__/c_cpp_properties.json +++ /dev/null @@ -1,23 +0,0 @@ -{ - "configurations": [ - { - "name": "ESP-IDF", - "compilerPath": "C:\\espidftools\\tools\\xtensa-esp-elf\\esp-13.2.0_20230928\\xtensa-esp-elf\\bin\\xtensa-esp32s3-elf-gcc.exe", - "compileCommands": "${config:idf.buildPath}/compile_commands.json", - "includePath": [ - "${config:idf.espIdfPath}/components/**", - "${config:idf.espIdfPathWin}/components/**", - "${workspaceFolder}/**" - ], - "browse": { - "path": [ - "${config:idf.espIdfPath}/components", - "${config:idf.espIdfPathWin}/components", - "${workspaceFolder}" - ], - "limitSymbolsToIncludedHeaders": true - } - } - ], - "version": 4 -} diff --git a/.vscode__/launch.json b/.vscode__/launch.json deleted file mode 100644 index 8720977..0000000 --- a/.vscode__/launch.json +++ /dev/null @@ -1,90 +0,0 @@ -{ - // Use IntelliSense to learn about possible attributes. - // Hover to view descriptions of existing attributes. - // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 - "version": "0.2.0", - "configurations": [ - { - "type": "gdbtarget", - "request": "attach", - "name": "Eclipse CDT GDB Adapter" - }, - { - "type": "gdb", - "request": "attach", - "name": "NativeDebug", - "target": "extended-remote :3333", - "executable": "${workspaceFolder}/build/${command:espIdf.getProjectName}.elf", - "gdbpath": "${command:espIdf.getToolchainGdb}", - "cwd": "${workspaceRoot}", - "autorun": [ - "mon reset halt", - "maintenance flush register-cache", - "thb app_main" - ] - }, - { - "name": "GDB", - "type": "cppdbg", - "request": "launch", - "MIMode": "gdb", - "miDebuggerPath": "${command:espIdf.getToolchainGdb}", - "requireExactSource": true, - "stopAtEntry": true, - "program": "${workspaceFolder}/build/${command:espIdf.getProjectName}.elf", - "windows": { - "program": "${workspaceFolder}\\build\\${command:espIdf.getProjectName}.elf" - }, - "cwd": "${workspaceFolder}", - "setupCommands": [ - { "text": "set remotetimeout 20" }, - ], - "postRemoteConnectCommands": [ - { "text": "mon reset halt" }, - { "text": "maintenance flush register-cache"}, - ], - "externalConsole": false, - "logging": { - "engineLogging": true - } - }, - { - "type": "espidf", - "name": "Launch", - "request": "launch", - "debugPort": 9998, - "logLevel": 2, - "mode": "manual", - "verifyAppBinBeforeDebug": false, - "tmoScaleFactor": 1, - "initGdbCommands": [ - "target remote :3333", - "set remotetimeout 20", - "symbol-file /path/to/program.elf", - "mon reset halt", - "maintenance flush register-cache", - "thb app_main" - ], - "env": { - "CUSTOM_ENV_VAR": "SOME_VALUE" - } - }, - { - "type": "gdbtarget", - "request": "attach", - "name": "Eclipse CDT Remote", - "program": "${workspaceFolder}/build/${command:espIdf.getProjectName}.elf", - "initCommands": [ - "set remotetimeout 20", - "set remote hardware-watchpoint-limit 2", - "mon reset halt", - "maintenance flush register-cache", - "thb app_main", - ], - "gdb": "${command:espIdf.getToolchainGdb}", - "target": { - "port": "3333" - }, - } - ] -} \ No newline at end of file diff --git a/.vscode__/settings.json b/.vscode__/settings.json deleted file mode 100644 index a125d26..0000000 --- a/.vscode__/settings.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "idf.adapterTargetName": "esp32s3", - "idf.flashType": "UART", - "idf.portWin": "COM11", - "files.associations": { - "string.h": "c" - }, - "idf.espIdfPathWin": "C:\\espidf\\v5.2.3\\esp-idf" -} diff --git a/README.md b/README.md index c01519b..33c2c98 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ -18px Montserrat + Home de FontAwesome - -``` docker run -v $PWD:/app -w /app lvfontconv lv_font_conv --bpp 4 --size 18 --no-compress --font Montserrat-Medium.ttf --symbols "0123456789.°éûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz '" --format lvgl -o montserrat_medium_18.c --font fa-solid-900.ttf --range 61461 ``` - -12px Montserrat - +18px Montserrat + Home de FontAwesome + +``` docker run -v $PWD:/app -w /app lvfontconv lv_font_conv --bpp 4 --size 18 --no-compress --font Montserrat-Medium.ttf --symbols "0123456789.°éûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz '" --format lvgl -o montserrat_medium_18.c --font fa-solid-900.ttf --range 61461 ``` + +12px Montserrat + ``` docker run -v $PWD:/app -w /app lvfontconv lv_font_conv --bpp 4 --size 12 --no-compress --font Montserrat-Medium.ttf --symbols "0123456789.°èéêûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz '" --format lvgl -o montserrat_medium_12.c ``` \ No newline at end of file diff --git a/ca_cert.pem b/ca_cert.pem new file mode 100644 index 0000000..f2e6347 --- /dev/null +++ b/ca_cert.pem @@ -0,0 +1,22 @@ +-----BEGIN CERTIFICATE----- +MIIDmTCCAoGgAwIBAgIUd5qKY6blEffPyHQZnmQfxkcCO7AwDQYJKoZIhvcNAQEL +BQAwXDELMAkGA1UEBhMCRlIxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoM +GEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZDEVMBMGA1UEAwwMMTkyLjE2OC4wLjI4 +MB4XDTI0MTExMzE4MjYxOVoXDTI1MTExMzE4MjYxOVowXDELMAkGA1UEBhMCRlIx +EzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdpdHMg +UHR5IEx0ZDEVMBMGA1UEAwwMMTkyLjE2OC4wLjI4MIIBIjANBgkqhkiG9w0BAQEF +AAOCAQ8AMIIBCgKCAQEA8lKPcpJ6/FhrI+E8fzR93N/XIfEW7GpFa+KNp+DK9DGS +hHno2yVGXNdUFRQEL/2pL8aiZzZ7xGMubzEIr1dlHrb/PplGRTXCxQWnDJDsOu4w +7TbzjYxDhgMwXhSGuFlMexFBh+W9qcO85l4wNSOhHusyf7XZaPAd3NGmK4XsoeXJ +DSROJLLpvyZM3yt1kuC3GTWSqUe4Ldv+kaAfyW+X/PJ7Tgb6frLGNCs5A0zLhFxb +FS2omnqX6+H2Bjvk3nCQr85zcuIrnXQ+Hy58MayS+dRqPTSNw7RqRVvrGUuQuj5y +/ruAVLjG6F9wTZZFJ8Nk2veuFxIG+8ADpglWoYrokQIDAQABo1MwUTAdBgNVHQ4E +FgQUUa64jnTc+VqWQB93Fp/yPuirm2cwHwYDVR0jBBgwFoAUUa64jnTc+VqWQB93 +Fp/yPuirm2cwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0BAQsFAAOCAQEAnqg9 +DeBozovXmwcbDTlTqz1b5LJ3Xz4mhUnEssmlDvvlXMqL1CjeXDKgOXtkWaomTJNO +MfMTmkkKg2lomNe2O84nUyPJnHYle5cbxZXAvbkmsi6R95lXFf5+bHAtU05TFYKc +BWMPB3Vwym9qrAc8G1LPr05LYgrJsQ9xkf0pVR7hrjgu9k6ElNAQSiH4dlyK4b/T +12U4zBawZNv3f6OnKOTq2NuwwzxWSwRRbEGUf0qO6Z8LNsj7yvmp2ImfN1e3a39p ++WmxJkHBzg5LxUon8jtiZLKeAPNlAPvKTs/4umE0LdZnsdlYrNR+kFeMMurxHvfZ +ykxPELUVUWEgv/IRbA== +-----END CERTIFICATE----- diff --git a/ca_key.pem b/ca_key.pem new file mode 100644 index 0000000..0dca181 --- /dev/null +++ b/ca_key.pem @@ -0,0 +1,28 @@ +-----BEGIN PRIVATE KEY----- +MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQDyUo9yknr8WGsj +4Tx/NH3c39ch8RbsakVr4o2n4Mr0MZKEeejbJUZc11QVFAQv/akvxqJnNnvEYy5v +MQivV2Uetv8+mUZFNcLFBacMkOw67jDtNvONjEOGAzBeFIa4WUx7EUGH5b2pw7zm +XjA1I6Ee6zJ/tdlo8B3c0aYrheyh5ckNJE4ksum/JkzfK3WS4LcZNZKpR7gt2/6R +oB/Jb5f88ntOBvp+ssY0KzkDTMuEXFsVLaiaepfr4fYGO+TecJCvznNy4iuddD4f +LnwxrJL51Go9NI3DtGpFW+sZS5C6PnL+u4BUuMboX3BNlkUnw2Ta964XEgb7wAOm +CVahiuiRAgMBAAECggEAHqYEkKgoN/xy6KHXRft8o9AH5LoafSJfz2pjIkWTRdlz +P6AvrHAFez6c2uGiOfOqT2mfJtDETK2CtPuNrqeuGXlpxSAbvCs1jDfPzg4SYs23 +kHkvyspfy/ZhSrTr6SsaOkKPeEG9gFhKbxSgokf0W/XBeFemvNgJ3uEBVGXm7P7l +MtwGTaM/wHRUqbLTxwzp++pzajs3YDZiU42TJP9hw2d6bBhRS0Jf0p8EAmDZRin2 +IdKl559pwLewfwfyDUd2ea4NpGVT7x5bX0vI0QKPfLbWyd5Q1+cv7dRi9EP8iB57 +anrrRHWFmq/+CX79CGMvbdt+3zqxFAgpDxLQ3gcIpQKBgQD5U9lKIUkFw6EqcNyq +Uz0+Z/0fXzhkABUBvzan+mbESYD+cnDzA2WX+bBgfmugcmWNTjUmW/6WC0ZhNQ/x +5SJz9OYKBmdkdg0XUm4ALhfwDvX6Pdq8A6NFHUg/y/ljjTC7n/qDkcB4L3/jENmX +ZT91biCV8574MUrqZk9FRInSDwKBgQD4zrhHgYcwD0iRFqSbUeaU/M/Vwh5ZyVlU +5+kXXsjfeXdMoTEeQaaWjkYjPzV+PcAw9BGQeS+GtOx18P/vuVvVGuFEgM1qBiGt +d1Ixb0sdzDDSP91tH1gXcYKM7DETIyOok+U48YTkEnsnxGk2iOjPHm1iu4mINKFa +YG/qm7u7XwKBgGY9Jesp/wGoGNyIb1RA0epXRgqpRzxqdDLFMCptmdp/sa+lSf+8 +stpA/zxyWrvubQomudDDBICOmwudcK5moVwfXn1Z5ufhKLkZihX00MgVunQlDR7v +9vGOcmQGxns2GHe3wEhXai9eevinnjJgyEblI+OZhOSNggTgcz0aP9GtAoGBAPHj +7+689BR6V1+PNvs2Fcm1O84iymUaRvov+UJaSUpSifR7Jgi3ZOEscu3jjvsrx8UQ +FF90IguBq/5CDmEewTQezPFPk+VHDsjZn5QmEk5m7PQLWRe1CGzKU1T0cAWd/RXw +q0LANCWT/h28a1m0ozpx54C8uMot+Mynw0bAnzRbAoGAG9rlCW9OBFIodxdAOUKH +8oJMF+hYBeyvzEdnZhhpShpnIWs0BKt2sWTFRoedLs5Pck3Y1VuOUWmSNhjLhd5X +f14tTFynLE42NL6eJ5FyFXLoogki4ObegIfgkFhrzHX4f6b6pD3GSDiXhru3ZjUr +mPOvd++V0fTVrC2DfTWaXV0= +-----END PRIVATE KEY----- diff --git a/components/esp_littlefs b/components/esp_littlefs deleted file mode 160000 index 28639dd..0000000 --- a/components/esp_littlefs +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 28639dd469af0b33df55d481da8383347e88067e diff --git a/components/image_downloader/CMakeLists.txt b/components/image_downloader/CMakeLists.txt index e4bf1a5..910bff1 100644 --- a/components/image_downloader/CMakeLists.txt +++ b/components/image_downloader/CMakeLists.txt @@ -1,3 +1,3 @@ -idf_component_register(SRCS "image_downloader.c" - INCLUDE_DIRS "include" - REQUIRES json esp_http_client esp-tls esp_timer ) +idf_component_register(SRCS "image_downloader.c" + INCLUDE_DIRS "include" + REQUIRES json esp_http_client esp-tls esp_timer ) diff --git a/components/image_downloader/image_downloader.c b/components/image_downloader/image_downloader.c index 5b6b8f2..ac59aa7 100644 --- a/components/image_downloader/image_downloader.c +++ b/components/image_downloader/image_downloader.c @@ -1,209 +1,211 @@ -// Note: Run menuconfig to set the WiFi Credentials -> CALE Configuration -// Requirements: Needs to have an EPD Class defined. Needs PSRAM. -// This example does not use a decoded buffer hence leaves more external RAM free -// At the same time it looses the JPG_DITHER functionality in favour of render speed. -// As default only configured for parallel epapers -#include "esp_heap_caps.h" -#include "esp_log.h" -#include "esp_types.h" -#include "freertos/FreeRTOS.h" -#include "freertos/task.h" -#include "freertos/event_groups.h" -#include "esp_sleep.h" -// WiFi related -#include "esp_event.h" -#include "esp_log.h" -#include "esp_timer.h" -#include "lwip/err.h" -#include "lwip/sys.h" -// HTTP Client + time -#include "esp_http_client.h" -#include "esp_sntp.h" - -#include -#include -#include - - -#define EXAMPLE_MAX_CHAR_SIZE 64 - - -// JPG decoder -#if ESP_IDF_VERSION_MAJOR >= 4 // IDF 4+ - #include "esp32/rom/tjpgd.h" -#else // ESP32 Before IDF 4.0 - #include "rom/tjpgd.h" -#endif - -#include "esp_task_wdt.h" -#include -#include -#include // round + pow -#include "image_downloader.h" - -#define MOUNT_POINT "/sdcard" -static const char *TAG = "ImgDwn"; - -// Image URL and jpg settings. Make sure to update EPD_WIDTH/HEIGHT if using loremflickr -// Note: Only HTTP protocol supported (Check README to use SSL secure URLs) loremflickr -#define STR_HELPER(x) #x -#define STR(x) STR_HELPER(x) - -#define IMGDWN_WIDTH 600 -#define IMGDWN_HEIGHT 460 -#define IMGDWN_URL2 ("http://vps-edf71efa.vps.ovh.net:3000/render/d-solo/7BtRMrv4k/temperatures?orgId=1&var-emplacement=entree_ECS&var-emplacement=entree_reseauSol&panelId=4&width=650&height=460&scale=1&tz=Europe%2FParis/") -#define IMGDWN_URL ("http://vps-edf71efa.vps.ovh.net:3000/render/d-solo/bOcPeysGz/hauteur-cuve?orgId=1&from=now-2d&refresh=1m&panelId=4&width=300&height=200&scale=1&tz=Europe%2FParis") // 650 460 -// As default is 512 without setting buffer_size property in esp_http_client_config_t -#define HTTP_RECEIVE_BUFFER_SIZE 1938 - -#define DEBUG_VERBOSE false - -// Buffers -uint8_t *fb; // EPD 2bpp buffer -uint8_t *source_buf; // JPG download buffer -uint8_t *decoded_image; // RAW decoded image - -uint32_t buffer_pos = 0; -uint32_t time_download = 0; -uint32_t time_decomp = 0; -uint32_t time_render = 0; - -uint16_t countDataEventCalls = 0; -uint32_t countDataBytes = 0; -uint32_t img_buf_pos = 0; -uint32_t dataLenTotal = 0; -uint64_t startTime = 0; - - void create_file_app(uint8_t *buffer, uint32_t size) - { - ESP_LOGI(TAG, "Opening file"); - //ESP_LOGI(TAG, "output buffer to spiffs: %s \n", buffer); - FILE* f = fopen(MOUNT_POINT"/hello2.png", "wb+"); - if (f == NULL) { - ESP_LOGE(TAG, "Failed to open file for writing"); - return; - } - for(int i=0; ievent_id) - { - case HTTP_EVENT_ERROR: - ESP_LOGE(TAG, "HTTP_EVENT_ERROR"); - break; - case HTTP_EVENT_ON_CONNECTED: - ESP_LOGI(TAG, "HTTP_EVENT_ON_CONNECTED"); - break; - case HTTP_EVENT_HEADER_SENT: - ESP_LOGI(TAG, "HTTP_EVENT_HEADER_SENT"); - break; - case HTTP_EVENT_ON_HEADER: - #if DEBUG_VERBOSE - ESP_LOGI(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value); - #endif - break; - case HTTP_EVENT_ON_DATA: - ++countDataEventCalls; - #if DEBUG_VERBOSE - if (countDataEventCalls%10==0) { - ESP_LOGI(TAG, "%d len:%d\n", countDataEventCalls, evt->data_len); - } - #endif - dataLenTotal += evt->data_len; - - if (countDataEventCalls == 1) startTime = esp_timer_get_time(); - // Append received data into source_buf - memcpy(&source_buf[img_buf_pos], evt->data, evt->data_len); - img_buf_pos += evt->data_len; - - // Optional hexa dump - //ESP_LOG_BUFFER_HEX(TAG, source_buf, 100); - break; - - case HTTP_EVENT_REDIRECT: - break; - case HTTP_EVENT_ON_FINISH: - // Do not draw if it's a redirect (302) - if (esp_http_client_get_status_code(evt->client) == 200) { - printf("%li bytes read from %s\nIMG_BUF size: %li\n", img_buf_pos, IMGDWN_URL, img_buf_pos); - //drawBufJpeg(source_buf, 0, 0); - create_file_app(source_buf,img_buf_pos); //function which opens and records data to spiffs file - time_download = (esp_timer_get_time()-startTime)/1000; - ESP_LOGI("www-dw", "%li ms - download", time_download); - // Refresh display - //display.update(); - - ESP_LOGI("total", "%li ms - total time spent\n", time_download+time_decomp+time_render); - } else { - printf("HTTP on finish got status code: %d\n", esp_http_client_get_status_code(evt->client)); - } - break; - - case HTTP_EVENT_DISCONNECTED: - ESP_LOGI(TAG, "HTTP_EVENT_DISCONNECTED\n"); - break; - } - return ESP_OK; -} - -// Handles http request -static void download(void) -{ - esp_http_client_config_t config = { - .url = IMGDWN_URL, - .disable_auto_redirect = false, - .event_handler = _http_event_handler_id, - .buffer_size = HTTP_RECEIVE_BUFFER_SIZE, - .timeout_ms = 50000 - }; - - esp_http_client_handle_t client = esp_http_client_init(&config); - - #if DEBUG_VERBOSE - printf("Free heap before HTTP download: %d\n", xPortGetFreeHeapSize()); - #endif - - esp_err_t err = esp_http_client_perform(client); - if (err == ESP_OK) - { - ESP_LOGI(TAG, "\nIMAGE URL: %s\n\nHTTP GET Status = %d, content_length = %lli\n", - IMGDWN_URL, - esp_http_client_get_status_code(client), - esp_http_client_get_content_length(client)); - } - else - { - ESP_LOGE(TAG, "\nHTTP GET request failed: %s", esp_err_to_name(err)); - } - - //printf("Go to sleep %d minutes\n", CONFIG_DEEPSLEEP_MINUTES_AFTER_RENDER); - esp_http_client_cleanup(client); - vTaskDelay(3600000 / portTICK_PERIOD_MS); - //deepsleep(); -} - -void imgdwn(void *pvParameter) { - - ESP_LOGE(TAG, "beginning"); - - // Should be big enough to allocate the JPEG file size, width * height should suffice - source_buf = (uint8_t *)heap_caps_malloc(IMGDWN_HEIGHT * IMGDWN_WIDTH, MALLOC_CAP_SPIRAM); - if (source_buf == NULL) { - ESP_LOGE(TAG, "Initial alloc source_buf failed!"); - } - printf("Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - - download(); - - heap_caps_free(source_buf); - printf("Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - - +// Note: Run menuconfig to set the WiFi Credentials -> CALE Configuration +// Requirements: Needs to have an EPD Class defined. Needs PSRAM. +// This example does not use a decoded buffer hence leaves more external RAM free +// At the same time it looses the JPG_DITHER functionality in favour of render speed. +// As default only configured for parallel epapers +#include "esp_heap_caps.h" +#include "esp_log.h" +#include "esp_types.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/event_groups.h" +#include "esp_sleep.h" +// WiFi related +#include "esp_event.h" +#include "esp_log.h" +#include "esp_timer.h" +#include "lwip/err.h" +#include "lwip/sys.h" +// HTTP Client + time +#include "esp_http_client.h" +#include "esp_sntp.h" + +#include +#include +#include + + +#define EXAMPLE_MAX_CHAR_SIZE 64 + + +// JPG decoder +#if ESP_IDF_VERSION_MAJOR >= 4 // IDF 4+ + #include "esp32/rom/tjpgd.h" +#else // ESP32 Before IDF 4.0 + #include "rom/tjpgd.h" +#endif + +#include "esp_task_wdt.h" +#include +#include +#include // round + pow +#include "image_downloader.h" + +#define MOUNT_POINT "/sdcard" +static const char *TAG = "ImgDwn"; + +// Image URL and jpg settings. Make sure to update EPD_WIDTH/HEIGHT if using loremflickr +// Note: Only HTTP protocol supported (Check README to use SSL secure URLs) loremflickr +#define STR_HELPER(x) #x +#define STR(x) STR_HELPER(x) + +#define IMGDWN_WIDTH_STR "620" +#define IMGDWN_WIDTH 620 +#define IMGDWN_HEIGHT_STR "460" +#define IMGDWN_HEIGHT 460 +#define IMGDWN_URL2 ("http://vps-edf71efa.vps.ovh.net:3000/render/d-solo/7BtRMrv4k/temperatures?orgId=1&var-emplacement=entree_ECS&var-emplacement=entree_reseauSol&panelId=4&width=650&height=460&scale=1&tz=Europe%2FParis/") +#define IMGDWN_URL ("http://vps-edf71efa.vps.ovh.net:3000/render/d-solo/bOcPeysGz/hauteur-cuve?orgId=1&from=now-2d&refresh=1m&panelId=4&width=" IMGDWN_WIDTH_STR "&height=" IMGDWN_HEIGHT_STR "&scale=1&tz=Europe%2FParis") // 650 460 +// As default is 512 without setting buffer_size property in esp_http_client_config_t +#define HTTP_RECEIVE_BUFFER_SIZE 1938 + +#define DEBUG_VERBOSE false + +// Buffers +uint8_t *fb; // EPD 2bpp buffer +uint8_t *source_buf; // JPG download buffer +uint8_t *decoded_image; // RAW decoded image + +uint32_t buffer_pos = 0; +uint32_t time_download = 0; +uint32_t time_decomp = 0; +uint32_t time_render = 0; + +uint16_t countDataEventCalls = 0; +uint32_t countDataBytes = 0; +uint32_t img_buf_pos = 0; +uint32_t dataLenTotal = 0; +uint64_t startTime = 0; + + void create_file_app(uint8_t *buffer, uint32_t size) + { + ESP_LOGI(TAG, "Opening file"); + //ESP_LOGI(TAG, "output buffer to spiffs: %s \n", buffer); + FILE* f = fopen(MOUNT_POINT"/hello2.png", "wb+"); + if (f == NULL) { + ESP_LOGE(TAG, "Failed to open file for writing"); + return; + } + for(int i=0; ievent_id) + { + case HTTP_EVENT_ERROR: + ESP_LOGE(TAG, "HTTP_EVENT_ERROR"); + break; + case HTTP_EVENT_ON_CONNECTED: + ESP_LOGI(TAG, "HTTP_EVENT_ON_CONNECTED"); + break; + case HTTP_EVENT_HEADER_SENT: + ESP_LOGI(TAG, "HTTP_EVENT_HEADER_SENT"); + break; + case HTTP_EVENT_ON_HEADER: + #if DEBUG_VERBOSE + ESP_LOGI(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value); + #endif + break; + case HTTP_EVENT_ON_DATA: + ++countDataEventCalls; + #if DEBUG_VERBOSE + if (countDataEventCalls%10==0) { + ESP_LOGI(TAG, "%d len:%d\n", countDataEventCalls, evt->data_len); + } + #endif + dataLenTotal += evt->data_len; + + if (countDataEventCalls == 1) startTime = esp_timer_get_time(); + // Append received data into source_buf + memcpy(&source_buf[img_buf_pos], evt->data, evt->data_len); + img_buf_pos += evt->data_len; + + // Optional hexa dump + //ESP_LOG_BUFFER_HEX(TAG, source_buf, 100); + break; + + case HTTP_EVENT_REDIRECT: + break; + case HTTP_EVENT_ON_FINISH: + // Do not draw if it's a redirect (302) + if (esp_http_client_get_status_code(evt->client) == 200) { + printf("%li bytes read from %s\nIMG_BUF size: %li\n", img_buf_pos, IMGDWN_URL, img_buf_pos); + //drawBufJpeg(source_buf, 0, 0); + create_file_app(source_buf,img_buf_pos); //function which opens and records data to spiffs file + time_download = (esp_timer_get_time()-startTime)/1000; + ESP_LOGI("www-dw", "%li ms - download", time_download); + // Refresh display + //display.update(); + + ESP_LOGI("total", "%li ms - total time spent\n", time_download+time_decomp+time_render); + } else { + printf("HTTP on finish got status code: %d\n", esp_http_client_get_status_code(evt->client)); + } + break; + + case HTTP_EVENT_DISCONNECTED: + ESP_LOGI(TAG, "HTTP_EVENT_DISCONNECTED\n"); + break; + } + return ESP_OK; +} + +// Handles http request +static void download(void) +{ + esp_http_client_config_t config = { + .url = IMGDWN_URL, + .disable_auto_redirect = false, + .event_handler = _http_event_handler_id, + .buffer_size = HTTP_RECEIVE_BUFFER_SIZE, + .timeout_ms = 50000 + }; + + esp_http_client_handle_t client = esp_http_client_init(&config); + + #if DEBUG_VERBOSE + printf("Free heap before HTTP download: %d\n", xPortGetFreeHeapSize()); + #endif + + esp_err_t err = esp_http_client_perform(client); + if (err == ESP_OK) + { + ESP_LOGI(TAG, "\nIMAGE URL: %s\n\nHTTP GET Status = %d, content_length = %lli\n", + IMGDWN_URL, + esp_http_client_get_status_code(client), + esp_http_client_get_content_length(client)); + } + else + { + ESP_LOGE(TAG, "\nHTTP GET request failed: %s", esp_err_to_name(err)); + } + + //printf("Go to sleep %d minutes\n", CONFIG_DEEPSLEEP_MINUTES_AFTER_RENDER); + esp_http_client_cleanup(client); + vTaskDelay(3600000 / portTICK_PERIOD_MS); + //deepsleep(); +} + +void imgdwn(void *pvParameter) { + + ESP_LOGE(TAG, "beginning"); + + // Should be big enough to allocate the JPEG file size, width * height should suffice + source_buf = (uint8_t *)heap_caps_malloc(IMGDWN_HEIGHT * IMGDWN_WIDTH, MALLOC_CAP_SPIRAM); + if (source_buf == NULL) { + ESP_LOGE(TAG, "Initial alloc source_buf failed!"); + } + printf("Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + + download(); + + heap_caps_free(source_buf); + printf("Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + + } \ No newline at end of file diff --git a/components/image_downloader/include/image_downloader.h b/components/image_downloader/include/image_downloader.h index 903eec7..6af9130 100644 --- a/components/image_downloader/include/image_downloader.h +++ b/components/image_downloader/include/image_downloader.h @@ -1,2 +1,2 @@ -void imgdwn(); -#pragma once +void imgdwn(); +#pragma once diff --git a/components/littlefs b/components/littlefs deleted file mode 160000 index d01280e..0000000 --- a/components/littlefs +++ /dev/null @@ -1 +0,0 @@ -Subproject commit d01280e64934a09ba16cac60cf9d3a37e228bb66 diff --git a/components/meteofrance/CMakeLists.txt b/components/meteofrance/CMakeLists.txt index 36f4789..40575ad 100644 --- a/components/meteofrance/CMakeLists.txt +++ b/components/meteofrance/CMakeLists.txt @@ -1,3 +1,3 @@ -idf_component_register(SRCS "meteofrance.c" - INCLUDE_DIRS "include" - REQUIRES json esp_http_client esp-tls) +idf_component_register(SRCS "meteofrance.c" + INCLUDE_DIRS "include" + REQUIRES json esp_http_client esp-tls) diff --git a/components/meteofrance/include/meteofrance.h b/components/meteofrance/include/meteofrance.h index 6edaec9..bcc8694 100644 --- a/components/meteofrance/include/meteofrance.h +++ b/components/meteofrance/include/meteofrance.h @@ -1,61 +1,61 @@ - -#include "time.h" - -struct node { - struct node *next; - int e; - }; - -struct Hashtable { - unsigned Tablesize; - struct node *Cells; - }; - -struct dailyforecast_prev{ - float min; - float max; - char desc[25]; - char icon[9]; -}; - -struct forecast_prev{ - float value; - char desc[25]; - char icon[9]; -}; - -struct meteodailyforecast_data{ - time_t datetime; - bool isValid; - struct dailyforecast_prev previsions; -}; - -struct meteoforecast_data{ - time_t datetime; - bool isValid; - struct forecast_prev previsions; -}; - -typedef void (*weather_data_callback)(struct meteodailyforecast_data *datas, struct meteoforecast_data *datasf); -typedef void (*weather_data_start_callback)(); - -typedef struct { - unsigned int humidity; - float temperature; - float pressure; - unsigned long retreival_period; - weather_data_callback data_retreived_cb; - weather_data_start_callback data_retreived_cb_start; -} weather_data; - -void printdftemp(struct dailyforecast_prev *tmp); -void printftemp(struct forecast_prev *tmp); -void printfdf(struct meteodailyforecast_data *tmp); -void dtToString(time_t, char *buffer); -void dtHToString(time_t, char *buffer); -void printff(struct meteoforecast_data *tmp); - -void on_weather_data_retrieval(weather_data_callback data_retreived_cb); -void on_weather_data_retrieval_start(weather_data_callback data_retreived_cb); -void initialise_weather_data_retrieval(unsigned long retreival_period); - + +#include "time.h" + +struct node { + struct node *next; + int e; + }; + +struct Hashtable { + unsigned Tablesize; + struct node *Cells; + }; + +struct dailyforecast_prev{ + float min; + float max; + char desc[25]; + char icon[9]; +}; + +struct forecast_prev{ + float value; + char desc[25]; + char icon[9]; +}; + +struct meteodailyforecast_data{ + time_t datetime; + bool isValid; + struct dailyforecast_prev previsions; +}; + +struct meteoforecast_data{ + time_t datetime; + bool isValid; + struct forecast_prev previsions; +}; + +typedef void (*weather_data_callback)(struct meteodailyforecast_data *datas, struct meteoforecast_data *datasf); +typedef void (*weather_data_start_callback)(); + +typedef struct { + unsigned int humidity; + float temperature; + float pressure; + unsigned long retreival_period; + weather_data_callback data_retreived_cb; + weather_data_start_callback data_retreived_cb_start; +} weather_data; + +void printdftemp(struct dailyforecast_prev *tmp); +void printftemp(struct forecast_prev *tmp); +void printfdf(struct meteodailyforecast_data *tmp); +void dtToString(time_t, char *buffer); +void dtHToString(time_t, char *buffer); +void printff(struct meteoforecast_data *tmp); + +void on_weather_data_retrieval(weather_data_callback data_retreived_cb); +void on_weather_data_retrieval_start(weather_data_callback data_retreived_cb); +void initialise_weather_data_retrieval(unsigned long retreival_period); + diff --git a/components/meteofrance/meteofrance.c b/components/meteofrance/meteofrance.c index 53dd0f6..02b0d81 100644 --- a/components/meteofrance/meteofrance.c +++ b/components/meteofrance/meteofrance.c @@ -1,393 +1,397 @@ -/* - weather.c - Weather data retrieval from api.openweathermap.org - - This file is part of the ESP32 Everest Run project - https://github.com/krzychb/esp32-everest-run - - Copyright (c) 2016 Krzysztof Budzynski - This work is licensed under the Apache License, Version 2.0, January 2004 - See the file LICENSE for details. -*/ - -#include "freertos/FreeRTOS.h" -#include "freertos/task.h" -#include "esp_system.h" -#include "esp_log.h" - -#include -#include - -#include "meteofrance.h" -#include "cJSON.h" -#include "esp_http_client.h" -#include "esp_tls.h" - -static const char *TAG = "MeteoFrance"; - -/* Constants that aren't configurable in menuconfig - Typically only LOCATION_ID may need to be changed - */ -#define WEB_SERVER "webservice.meteofrance.com" //"192.168.0.10" //"www.example.com"// //"webservice.meteofrance.com" -#define WEB_PORT 80 // 5403 //80 -#define WEB_URL "/forecast" -#define TOKEN "__Wj7dVSTjV9YGu1guveLyDq0g7S7TfTjaHBTPTpO0kj8__" -// Location ID to get the weather data for -// #define LOCATION_ID "756135" -#define LATITUDE "49.22017054145735" -#define LONGITUDE "3.92188756221628" -#define WEB_QUERY "token=" TOKEN "&lat=" LATITUDE "&lon=" LONGITUDE - -#define MAX_HTTP_OUTPUT_BUFFER 32000 - -static weather_data weather; -static struct meteodailyforecast_data dailydatas[5]; -static struct meteoforecast_data forecastdatas[5]; - -inline int MIN(int a, int b) { return a > b ? b : a; } - -void printdftemp(struct dailyforecast_prev *tmp) -{ - printf(" Temps Min:%f, Max:%f", tmp->min, tmp->max); -} -void printftemp(struct forecast_prev *tmp) -{ - printf(" Temps Value:%f", tmp->value); -} -#define MAX_SIZE 80 - -void printfdf(struct meteodailyforecast_data *tmp) -{ - char buffer[MAX_SIZE]; - time_t timeToTransform = tmp->datetime; - dtToString(timeToTransform,buffer); - //ESP_LOGE(TAG, "%s", strftime_buf); - printf("IsValid:%s date:%s, Min:%.1f Max:%.1f Desc:%s Icon: %s\n", tmp->isValid ? "true" : "false", buffer, tmp->previsions.min, tmp->previsions.max, tmp->previsions.desc, tmp->previsions.icon); -} - -void dtToString(time_t ttt, char* buffer){ - struct tm timeinfo = {0}; - localtime_r(&ttt, &timeinfo); - strftime(buffer, MAX_SIZE, "%d/%m", &timeinfo); - //char strftime_buf[64]; - //sprintf(strftime_buf, "%d %d %d", timeinfo.tm_wday, timeinfo.tm_mday, timeinfo.tm_mon + 1); -} - -void dtHToString(time_t ttt, char* buffer){ - struct tm timeinfo = {0}; - localtime_r(&ttt, &timeinfo); - strftime(buffer, MAX_SIZE, "%H:%M", &timeinfo); - //char strftime_buf[64]; - //sprintf(strftime_buf, "%d %d %d", timeinfo.tm_wday, timeinfo.tm_mday, timeinfo.tm_mon + 1); -} - -void printff(struct meteoforecast_data *tmp) -{ - struct tm timeinfo = {0}; - localtime_r(&tmp->datetime, &timeinfo); - char buffer[MAX_SIZE]; - strftime(buffer, MAX_SIZE, "%c", &timeinfo); - char strftime_buf[64]; - sprintf(strftime_buf, "%d %d %d", timeinfo.tm_wday, timeinfo.tm_mday, timeinfo.tm_mon + 1); - ESP_LOGE(TAG, "%s", strftime_buf); - printf("IsValid:%s date:%s, Temp:%.1f Desc:%s\n", tmp->isValid ? "true" : "false", buffer, tmp->previsions.value, tmp->previsions.desc); -} - -esp_err_t _http_event_handler(esp_http_client_event_t *evt) -{ - static char *output_buffer; // Buffer to store response of http request from event handler - static int output_len; // Stores number of bytes read - switch (evt->event_id) - { - case HTTP_EVENT_ERROR: - ESP_LOGD(TAG, "HTTP_EVENT_ERROR"); - break; - case HTTP_EVENT_ON_CONNECTED: - ESP_LOGD(TAG, "HTTP_EVENT_ON_CONNECTED"); - break; - case HTTP_EVENT_HEADER_SENT: - ESP_LOGD(TAG, "HTTP_EVENT_HEADER_SENT"); - break; - case HTTP_EVENT_ON_HEADER: - ESP_LOGD(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value); - break; - case HTTP_EVENT_ON_DATA: - ESP_LOGD(TAG, "HTTP_EVENT_ON_DATA, len=%d", evt->data_len); - // Clean the buffer in case of a new request - if (output_len == 0 && evt->user_data) - { - // we are just starting to copy the output data into the use - memset(evt->user_data, 0, MAX_HTTP_OUTPUT_BUFFER); - } - /* - * Check for chunked encoding is added as the URL for chunked encoding used in this example returns binary data. - * However, event handler can also be used in case chunked encoding is used. - */ - if (!esp_http_client_is_chunked_response(evt->client)) - { - // If user_data buffer is configured, copy the response into the buffer - int copy_len = 0; - if (evt->user_data) - { - // The last byte in evt->user_data is kept for the NULL character in case of out-of-bound access. - copy_len = MIN(evt->data_len, (MAX_HTTP_OUTPUT_BUFFER - output_len)); - if (copy_len) - { - memcpy(evt->user_data + output_len, evt->data, copy_len); - } - } - else - { - int content_len = esp_http_client_get_content_length(evt->client); - if (output_buffer == NULL) - { - // We initialize output_buffer with 0 because it is used by strlen() and similar functions therefore should be null terminated. - output_buffer = (char *)calloc(content_len + 1, sizeof(char)); - output_len = 0; - if (output_buffer == NULL) - { - ESP_LOGE(TAG, "Failed to allocate memory for output buffer"); - return ESP_FAIL; - } - } - copy_len = MIN(evt->data_len, (content_len - output_len)); - if (copy_len) - { - memcpy(output_buffer + output_len, evt->data, copy_len); - } - } - output_len += copy_len; - } - - break; - case HTTP_EVENT_ON_FINISH: - ESP_LOGD(TAG, "HTTP_EVENT_ON_FINISH"); - if (output_buffer != NULL) - { - // Response is accumulated in output_buffer. Uncomment the below line to print the accumulated response - // ESP_LOG_BUFFER_HEX(TAG, output_buffer, output_len); - free(output_buffer); - output_buffer = NULL; - } - output_len = 0; - break; - case HTTP_EVENT_DISCONNECTED: - ESP_LOGI(TAG, "HTTP_EVENT_DISCONNECTED"); - int mbedtls_err = 0; - esp_err_t err = esp_tls_get_and_clear_last_error((esp_tls_error_handle_t)evt->data, &mbedtls_err, NULL); - if (err != 0) - { - ESP_LOGI(TAG, "Last esp error code: 0x%x", err); - ESP_LOGI(TAG, "Last mbedtls failure: 0x%x", mbedtls_err); - } - if (output_buffer != NULL) - { - free(output_buffer); - output_buffer = NULL; - } - output_len = 0; - break; - case HTTP_EVENT_REDIRECT: - ESP_LOGD(TAG, "HTTP_EVENT_REDIRECT"); - esp_http_client_set_header(evt->client, "From", "user@example.com"); - esp_http_client_set_header(evt->client, "Accept", "text/html"); - esp_http_client_set_redirection(evt->client); - break; - } - return ESP_OK; -} - -char *JSON_Types(int type) -{ - if (type == cJSON_Invalid) - return ("cJSON_Invalid"); - if (type == cJSON_False) - return ("cJSON_False"); - if (type == cJSON_True) - return ("cJSON_True"); - if (type == cJSON_NULL) - return ("cJSON_NULL"); - if (type == cJSON_Number) - return ("cJSON_Number"); - if (type == cJSON_String) - return ("cJSON_String"); - if (type == cJSON_Array) - return ("cJSON_Array"); - if (type == cJSON_Object) - return ("cJSON_Object"); - if (type == cJSON_Raw) - return ("cJSON_Raw"); - return NULL; -} - -void JSON_Parse(const cJSON *const root) -{ - // ESP_LOGI(TAG, "root->type=%s", JSON_Types(root->type)); - cJSON *current_element = NULL; - // ESP_LOGI(TAG, "roo->child=%p", root->child); - // ESP_LOGI(TAG, "roo->next =%p", root->next); - int i = 0; - - // Récupération previsions journalieres (15j par défaut mais on en récupere 3) - cJSON *df = cJSON_GetObjectItem(root, "daily_forecast"); - if (!cJSON_IsArray(df)) - { - ESP_LOGE(TAG, "Pas de tableau ^^"); - } - else - { - cJSON_ArrayForEach(current_element, df) - { - struct meteodailyforecast_data datasT; - // ESP_LOGI(TAG, "type=%s", JSON_Types(current_element->type)); - cJSON *dt = cJSON_GetObjectItem(current_element, "dt"); - if (cJSON_IsNumber(dt)) - { - datasT.datetime = dt->valueint; - cJSON *temps = cJSON_GetObjectItem(current_element, "T"); - datasT.previsions.min = cJSON_GetObjectItem(temps, "min")->valuedouble; - datasT.previsions.max = cJSON_GetObjectItem(temps, "max")->valuedouble; - - cJSON *weather12 = cJSON_GetObjectItem(current_element, "weather12H"); - strncpy(datasT.previsions.desc, cJSON_GetObjectItem(weather12, "desc")->valuestring, 24); - strncpy(datasT.previsions.icon, cJSON_GetObjectItem(weather12, "icon")->valuestring, 8); - datasT.isValid = true; - // ESP_LOGE(TAG,"Donnees lues"); - // printffd(&datasT); - dailydatas[i++] = datasT; - if (i == 3) - { - break; - } - } - } - } - // Récupération previsions du jour ("matin/midi/am/soir") - cJSON *fore = cJSON_GetObjectItem(root, "forecast"); - if(!cJSON_IsArray(fore)){ - ESP_LOGE(TAG, "Pas de tableau forecast"); - }else{ - i=0; - //On garde les données de 10h 14h 18h - cJSON_ArrayForEach(current_element, fore){ - struct meteoforecast_data datasT; - cJSON *dt = cJSON_GetObjectItem(current_element, "dt"); - if (cJSON_IsNumber(dt)) - { - datasT.datetime = dt->valueint; - struct tm timeinfo = {0}; - localtime_r(&(datasT.datetime), &timeinfo); - if(timeinfo.tm_hour==10 || timeinfo.tm_hour==14 || timeinfo.tm_hour==18){ - cJSON *temps = cJSON_GetObjectItem(current_element, "T"); - datasT.previsions.value = cJSON_GetObjectItem(temps, "value")->valuedouble; - cJSON *weather = cJSON_GetObjectItem(current_element, "weather"); - strncpy(datasT.previsions.desc, cJSON_GetObjectItem(weather, "desc")->valuestring, 24); - strncpy(datasT.previsions.icon, cJSON_GetObjectItem(weather, "icon")->valuestring, 8); - datasT.isValid = true; - // ESP_LOGE(TAG,"Donnees lues"); - // printffd(&datasT); - forecastdatas[i++] = datasT; - printff(&datasT); - if (i == 3) - { - break; - } - }else{ - //ESP_LOGE(TAG,"heure = %i on ne garde pas...", timeinfo.tm_hour); - //char buffer[MAX_SIZE]; - //strftime(buffer, MAX_SIZE, "%c", &timeinfo); - //printf("date:%s %lli", buffer, datasT.datetime); - } - - }else{ - ESP_LOGI(TAG,"dt n'est pas au format attendu ^^"); - } - } - ESP_LOGI(TAG, "Prévisions lues !"); - - } -} - -static bool process_response_body(const char *body) -{ - cJSON *root = cJSON_Parse(body); - JSON_Parse(root); - cJSON_Delete(root); - return true; -} - -static void http_request_task(void *pvParameter) -{ - while (1) - { - ESP_LOGE(TAG, "Début recup méteo --------------------------"); - weather.data_retreived_cb_start(NULL); - char *local_response_buffer = heap_caps_malloc((MAX_HTTP_OUTPUT_BUFFER + 1) * (sizeof(char)), MALLOC_CAP_SPIRAM); - // char local_response_buffer[MAX_HTTP_OUTPUT_BUFFER + 1] = {0}; - /** - * NOTE: All the configuration parameters for http_client must be spefied either in URL or as host and path parameters. - * If host and path parameters are not set, query parameter will be ignored. In such cases, - * query parameter should be specified in URL. - * - * If URL as well as host and path parameters are specified, values of host and path will be considered. - */ - esp_http_client_config_t config = { - .host = WEB_SERVER, - .port = WEB_PORT, - .path = WEB_URL, - .query = WEB_QUERY, - .event_handler = _http_event_handler, - .user_data = local_response_buffer, // Pass address of local buffer to get response - .disable_auto_redirect = true, - }; - esp_http_client_handle_t client = esp_http_client_init(&config); - char url[50]; - esp_http_client_get_url(client, url, 50); - ESP_LOGE(TAG, "%s", url); - - // GET - esp_err_t err = esp_http_client_perform(client); - if (err == ESP_OK) - { - ESP_LOGI(TAG, "HTTP GET Status = %d, content_length = %" PRId64, - esp_http_client_get_status_code(client), - esp_http_client_get_content_length(client)); - } - else - { - ESP_LOGE(TAG, "HTTP GET request failed: %s", esp_err_to_name(err)); - } - // ESP_LOGE(TAG, "%s",local_response_buffer); - - process_response_body(local_response_buffer); - weather.data_retreived_cb(dailydatas, forecastdatas); - heap_caps_free(local_response_buffer); - esp_http_client_cleanup(client); - - // http_client_request(&http_client, WEB_SERVER, get_request); - vTaskDelay(weather.retreival_period / portTICK_PERIOD_MS); - } -} - -void on_weather_data_retrieval(weather_data_callback data_retreived_cb) -{ - weather.data_retreived_cb = data_retreived_cb; -} - -void on_weather_data_retrieval_start(weather_data_callback data_retreived_cb_start) -{ - weather.data_retreived_cb_start = data_retreived_cb_start; -} - -void initialise_weather_data_retrieval(unsigned long retreival_period) -{ - weather.retreival_period = retreival_period; - - // http_client_on_process_chunk(&http_client, process_chunk); - // http_client_on_disconnected(&http_client, disconnected); - TaskHandle_t xHandle = NULL; - BaseType_t ret1 = xTaskCreate(&http_request_task, "http_request_task", 5 * 1024, NULL, 5, &xHandle); - if(ret1!=pdPASS ){ - ESP_LOGE(TAG, "Impossible de creer la tache %i", ret1); - } - ESP_LOGI(TAG, "HTTP request task started"); -} +/* + weather.c - Weather data retrieval from api.openweathermap.org + + This file is part of the ESP32 Everest Run project + https://github.com/krzychb/esp32-everest-run + + Copyright (c) 2016 Krzysztof Budzynski + This work is licensed under the Apache License, Version 2.0, January 2004 + See the file LICENSE for details. +*/ + +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "esp_system.h" +#include "esp_log.h" + +#include +#include + +#include "meteofrance.h" +#include "cJSON.h" +#include "esp_http_client.h" +#include "esp_tls.h" + +static const char *TAG = "MeteoFrance"; + +/* Constants that aren't configurable in menuconfig + Typically only LOCATION_ID may need to be changed + */ +#define WEB_SERVER "webservice.meteofrance.com" //"192.168.0.10" //"www.example.com"// //"webservice.meteofrance.com" +#define WEB_PORT 80 // 5403 //80 +#define WEB_URL "/forecast" +#define TOKEN "__Wj7dVSTjV9YGu1guveLyDq0g7S7TfTjaHBTPTpO0kj8__" +// Location ID to get the weather data for +// #define LOCATION_ID "756135" +#define LATITUDE "49.22017054145735" +#define LONGITUDE "3.92188756221628" +#define WEB_QUERY "token=" TOKEN "&lat=" LATITUDE "&lon=" LONGITUDE + +#define MAX_HTTP_OUTPUT_BUFFER 32000 + +static weather_data weather; +static struct meteodailyforecast_data dailydatas[5]; +static struct meteoforecast_data forecastdatas[5]; + +inline int MIN(int a, int b) { return a > b ? b : a; } + +void printdftemp(struct dailyforecast_prev *tmp) +{ + printf(" Temps Min:%f, Max:%f", tmp->min, tmp->max); +} +void printftemp(struct forecast_prev *tmp) +{ + printf(" Temps Value:%f", tmp->value); +} +#define MAX_SIZE 80 + +void printfdf(struct meteodailyforecast_data *tmp) +{ + char buffer[MAX_SIZE]; + time_t timeToTransform = tmp->datetime; + dtToString(timeToTransform,buffer); + //ESP_LOGE(TAG, "%s", strftime_buf); + printf("IsValid:%s date:%s, Min:%.1f Max:%.1f Desc:%s Icon: %s\n", tmp->isValid ? "true" : "false", buffer, tmp->previsions.min, tmp->previsions.max, tmp->previsions.desc, tmp->previsions.icon); +} + +void dtToString(time_t ttt, char* buffer){ + struct tm timeinfo = {0}; + localtime_r(&ttt, &timeinfo); + strftime(buffer, MAX_SIZE, "%d/%m", &timeinfo); + //char strftime_buf[64]; + //sprintf(strftime_buf, "%d %d %d", timeinfo.tm_wday, timeinfo.tm_mday, timeinfo.tm_mon + 1); +} + +void dtHToString(time_t ttt, char* buffer){ + struct tm timeinfo = {0}; + localtime_r(&ttt, &timeinfo); + strftime(buffer, MAX_SIZE, "%H:%M", &timeinfo); + //char strftime_buf[64]; + //sprintf(strftime_buf, "%d %d %d", timeinfo.tm_wday, timeinfo.tm_mday, timeinfo.tm_mon + 1); +} + +void printff(struct meteoforecast_data *tmp) +{ + struct tm timeinfo = {0}; + localtime_r(&tmp->datetime, &timeinfo); + char buffer[MAX_SIZE]; + strftime(buffer, MAX_SIZE, "%c", &timeinfo); + char strftime_buf[64]; + sprintf(strftime_buf, "%d %d %d", timeinfo.tm_wday, timeinfo.tm_mday, timeinfo.tm_mon + 1); + ESP_LOGE(TAG, "%s", strftime_buf); + printf("IsValid:%s date:%s, Temp:%.1f Desc:%s\n", tmp->isValid ? "true" : "false", buffer, tmp->previsions.value, tmp->previsions.desc); +} + +esp_err_t _http_event_handler(esp_http_client_event_t *evt) +{ + static char *output_buffer; // Buffer to store response of http request from event handler + static int output_len; // Stores number of bytes read + switch (evt->event_id) + { + case HTTP_EVENT_ERROR: + ESP_LOGD(TAG, "HTTP_EVENT_ERROR"); + break; + case HTTP_EVENT_ON_CONNECTED: + ESP_LOGD(TAG, "HTTP_EVENT_ON_CONNECTED"); + break; + case HTTP_EVENT_HEADER_SENT: + ESP_LOGD(TAG, "HTTP_EVENT_HEADER_SENT"); + break; + case HTTP_EVENT_ON_HEADER: + ESP_LOGD(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value); + break; + case HTTP_EVENT_ON_DATA: + ESP_LOGD(TAG, "HTTP_EVENT_ON_DATA, len=%d", evt->data_len); + // Clean the buffer in case of a new request + if (output_len == 0 && evt->user_data) + { + // we are just starting to copy the output data into the use + memset(evt->user_data, 0, MAX_HTTP_OUTPUT_BUFFER); + } + /* + * Check for chunked encoding is added as the URL for chunked encoding used in this example returns binary data. + * However, event handler can also be used in case chunked encoding is used. + */ + if (!esp_http_client_is_chunked_response(evt->client)) + { + // If user_data buffer is configured, copy the response into the buffer + int copy_len = 0; + if (evt->user_data) + { + // The last byte in evt->user_data is kept for the NULL character in case of out-of-bound access. + copy_len = MIN(evt->data_len, (MAX_HTTP_OUTPUT_BUFFER - output_len)); + if (copy_len) + { + memcpy(evt->user_data + output_len, evt->data, copy_len); + } + } + else + { + int content_len = esp_http_client_get_content_length(evt->client); + if (output_buffer == NULL) + { + // We initialize output_buffer with 0 because it is used by strlen() and similar functions therefore should be null terminated. + output_buffer = (char *)calloc(content_len + 1, sizeof(char)); + output_len = 0; + if (output_buffer == NULL) + { + ESP_LOGE(TAG, "Failed to allocate memory for output buffer"); + return ESP_FAIL; + } + } + copy_len = MIN(evt->data_len, (content_len - output_len)); + if (copy_len) + { + memcpy(output_buffer + output_len, evt->data, copy_len); + } + } + output_len += copy_len; + } + + break; + case HTTP_EVENT_ON_FINISH: + ESP_LOGD(TAG, "HTTP_EVENT_ON_FINISH"); + if (output_buffer != NULL) + { + // Response is accumulated in output_buffer. Uncomment the below line to print the accumulated response + // ESP_LOG_BUFFER_HEX(TAG, output_buffer, output_len); + free(output_buffer); + output_buffer = NULL; + } + output_len = 0; + break; + case HTTP_EVENT_DISCONNECTED: + ESP_LOGI(TAG, "HTTP_EVENT_DISCONNECTED"); + int mbedtls_err = 0; + esp_err_t err = esp_tls_get_and_clear_last_error((esp_tls_error_handle_t)evt->data, &mbedtls_err, NULL); + if (err != 0) + { + ESP_LOGI(TAG, "Last esp error code: 0x%x", err); + ESP_LOGI(TAG, "Last mbedtls failure: 0x%x", mbedtls_err); + } + if (output_buffer != NULL) + { + free(output_buffer); + output_buffer = NULL; + } + output_len = 0; + break; + case HTTP_EVENT_REDIRECT: + ESP_LOGD(TAG, "HTTP_EVENT_REDIRECT"); + esp_http_client_set_header(evt->client, "From", "user@example.com"); + esp_http_client_set_header(evt->client, "Accept", "text/html"); + esp_http_client_set_redirection(evt->client); + break; + } + return ESP_OK; +} + +char *JSON_Types(int type) +{ + if (type == cJSON_Invalid) + return ("cJSON_Invalid"); + if (type == cJSON_False) + return ("cJSON_False"); + if (type == cJSON_True) + return ("cJSON_True"); + if (type == cJSON_NULL) + return ("cJSON_NULL"); + if (type == cJSON_Number) + return ("cJSON_Number"); + if (type == cJSON_String) + return ("cJSON_String"); + if (type == cJSON_Array) + return ("cJSON_Array"); + if (type == cJSON_Object) + return ("cJSON_Object"); + if (type == cJSON_Raw) + return ("cJSON_Raw"); + return NULL; +} + +void JSON_Parse(const cJSON *const root) +{ + // ESP_LOGI(TAG, "root->type=%s", JSON_Types(root->type)); + cJSON *current_element = NULL; + // ESP_LOGI(TAG, "roo->child=%p", root->child); + // ESP_LOGI(TAG, "roo->next =%p", root->next); + int i = 0; + + // Récupération previsions journalieres (15j par défaut mais on en récupere 3) + cJSON *df = cJSON_GetObjectItem(root, "daily_forecast"); + if (!cJSON_IsArray(df)) + { + ESP_LOGE(TAG, "Pas de tableau ^^"); + } + else + { + cJSON_ArrayForEach(current_element, df) + { + struct meteodailyforecast_data datasT; + // ESP_LOGI(TAG, "type=%s", JSON_Types(current_element->type)); + cJSON *dt = cJSON_GetObjectItem(current_element, "dt"); + if (cJSON_IsNumber(dt)) + { + datasT.datetime = dt->valueint; + cJSON *temps = cJSON_GetObjectItem(current_element, "T"); + datasT.previsions.min = cJSON_GetObjectItem(temps, "min")->valuedouble; + datasT.previsions.max = cJSON_GetObjectItem(temps, "max")->valuedouble; + + cJSON *weather12 = cJSON_GetObjectItem(current_element, "weather12H"); + strncpy(datasT.previsions.desc, cJSON_GetObjectItem(weather12, "desc")->valuestring, 24); + strncpy(datasT.previsions.icon, cJSON_GetObjectItem(weather12, "icon")->valuestring, 8); + datasT.isValid = true; + // ESP_LOGE(TAG,"Donnees lues"); + // printffd(&datasT); + dailydatas[i++] = datasT; + if (i == 3) + { + break; + } + } + } + } + // Récupération previsions du jour ("matin/midi/am/soir") + cJSON *fore = cJSON_GetObjectItem(root, "forecast"); + if(!cJSON_IsArray(fore)){ + ESP_LOGE(TAG, "Pas de tableau forecast"); + }else{ + i=0; + //On garde les données de 10h 14h 18h + cJSON_ArrayForEach(current_element, fore){ + struct meteoforecast_data datasT; + cJSON *dt = cJSON_GetObjectItem(current_element, "dt"); + if (cJSON_IsNumber(dt)) + { + datasT.datetime = dt->valueint; + struct tm timeinfo = {0}; + localtime_r(&(datasT.datetime), &timeinfo); + if(timeinfo.tm_hour==10 || timeinfo.tm_hour==14 || timeinfo.tm_hour==18){ + cJSON *temps = cJSON_GetObjectItem(current_element, "T"); + datasT.previsions.value = cJSON_GetObjectItem(temps, "value")->valuedouble; + cJSON *weather = cJSON_GetObjectItem(current_element, "weather"); + strncpy(datasT.previsions.desc, cJSON_GetObjectItem(weather, "desc")->valuestring, 24); + strncpy(datasT.previsions.icon, cJSON_GetObjectItem(weather, "icon")->valuestring, 8); + datasT.isValid = true; + // ESP_LOGE(TAG,"Donnees lues"); + // printffd(&datasT); + forecastdatas[i++] = datasT; + printff(&datasT); + if (i == 3) + { + break; + } + }else{ + //ESP_LOGE(TAG,"heure = %i on ne garde pas...", timeinfo.tm_hour); + //char buffer[MAX_SIZE]; + //strftime(buffer, MAX_SIZE, "%c", &timeinfo); + //printf("date:%s %lli", buffer, datasT.datetime); + } + + }else{ + ESP_LOGI(TAG,"dt n'est pas au format attendu ^^"); + } + } + ESP_LOGI(TAG, "Prévisions lues !"); + + } +} + +static bool process_response_body(const char *body) +{ + cJSON *root = cJSON_Parse(body); + JSON_Parse(root); + cJSON_Delete(root); + return true; +} + +static void http_request_task(void *pvParameter) +{ + while (1) + { + ESP_LOGE(TAG, "Début recup méteo --------------------------"); + weather.data_retreived_cb_start(NULL); + char *local_response_buffer = heap_caps_malloc((MAX_HTTP_OUTPUT_BUFFER + 1) * (sizeof(char)), MALLOC_CAP_SPIRAM); + // char local_response_buffer[MAX_HTTP_OUTPUT_BUFFER + 1] = {0}; + /** + * NOTE: All the configuration parameters for http_client must be spefied either in URL or as host and path parameters. + * If host and path parameters are not set, query parameter will be ignored. In such cases, + * query parameter should be specified in URL. + * + * If URL as well as host and path parameters are specified, values of host and path will be considered. + */ + esp_http_client_config_t config = { + .host = WEB_SERVER, + .port = WEB_PORT, + .path = WEB_URL, + .query = WEB_QUERY, + .event_handler = _http_event_handler, + .user_data = local_response_buffer, // Pass address of local buffer to get response + .disable_auto_redirect = true, + }; + esp_http_client_handle_t client = esp_http_client_init(&config); + char url[50]; + esp_http_client_get_url(client, url, 50); + ESP_LOGE(TAG, "%s", url); + + // GET + esp_err_t err = esp_http_client_perform(client); + if (err == ESP_OK) + { + ESP_LOGI(TAG, "HTTP GET Status = %d, content_length = %" PRId64, + esp_http_client_get_status_code(client), + esp_http_client_get_content_length(client)); + } + else + { + ESP_LOGE(TAG, "HTTP GET request failed: %s", esp_err_to_name(err)); + } + // ESP_LOGE(TAG, "%s",local_response_buffer); + + process_response_body(local_response_buffer); + heap_caps_free(local_response_buffer); + esp_http_client_cleanup(client); + if(dailydatas->isValid){ + weather.data_retreived_cb(dailydatas, forecastdatas); + vTaskDelay(weather.retreival_period / portTICK_PERIOD_MS); + }else{ + //Ca a échoué on recommence dans 30 secondes + vTaskDelay(30000 / portTICK_PERIOD_MS); + } + + } +} + +void on_weather_data_retrieval(weather_data_callback data_retreived_cb) +{ + weather.data_retreived_cb = data_retreived_cb; +} + +void on_weather_data_retrieval_start(weather_data_callback data_retreived_cb_start) +{ + weather.data_retreived_cb_start = data_retreived_cb_start; +} + +void initialise_weather_data_retrieval(unsigned long retreival_period) +{ + weather.retreival_period = retreival_period; + + // http_client_on_process_chunk(&http_client, process_chunk); + // http_client_on_disconnected(&http_client, disconnected); + TaskHandle_t xHandle = NULL; + BaseType_t ret1 = xTaskCreate(&http_request_task, "http_request_task", 5 * 1024, NULL, 5, &xHandle); + if(ret1!=pdPASS ){ + ESP_LOGE(TAG, "Impossible de creer la tache %i", ret1); + } + ESP_LOGI(TAG, "HTTP request task started"); +} diff --git a/components/protocol_examples_common/CMakeLists.txt b/components/protocol_examples_common/CMakeLists.txt new file mode 100644 index 0000000..d8bccb1 --- /dev/null +++ b/components/protocol_examples_common/CMakeLists.txt @@ -0,0 +1,44 @@ +idf_build_get_property(target IDF_TARGET) + +if(${target} STREQUAL "linux") + # Header only library for linux + + idf_component_register(INCLUDE_DIRS include + SRCS protocol_examples_utils.c) + return() +endif() + +set(srcs "stdin_out.c" + "addr_from_stdin.c" + "connect.c" + "wifi_connect.c" + "protocol_examples_utils.c") + +if(CONFIG_EXAMPLE_PROVIDE_WIFI_CONSOLE_CMD) + list(APPEND srcs "console_cmd.c") +endif() + +if(CONFIG_EXAMPLE_CONNECT_ETHERNET) + list(APPEND srcs "eth_connect.c") +endif() + +if(CONFIG_EXAMPLE_CONNECT_PPP) + list(APPEND srcs "ppp_connect.c") +endif() + + +idf_component_register(SRCS "${srcs}" + INCLUDE_DIRS "include" + PRIV_REQUIRES esp_netif driver esp_wifi vfs console esp_eth) + +if(CONFIG_EXAMPLE_PROVIDE_WIFI_CONSOLE_CMD) + idf_component_optional_requires(PRIVATE console) +endif() + +if(CONFIG_EXAMPLE_CONNECT_ETHERNET) + idf_component_optional_requires(PUBLIC esp_eth) +endif() + +if(CONFIG_EXAMPLE_CONNECT_PPP) + idf_component_optional_requires(PRIVATE esp_tinyusb espressif__esp_tinyusb) +endif() diff --git a/components/protocol_examples_common/Kconfig.projbuild b/components/protocol_examples_common/Kconfig.projbuild new file mode 100644 index 0000000..1b450b9 --- /dev/null +++ b/components/protocol_examples_common/Kconfig.projbuild @@ -0,0 +1,425 @@ +menu "Example Connection Configuration" + + orsource "$IDF_PATH/examples/common_components/env_caps/$IDF_TARGET/Kconfig.env_caps" + + config EXAMPLE_CONNECT_WIFI + bool "connect using WiFi interface" + depends on !IDF_TARGET_LINUX && (SOC_WIFI_SUPPORTED || ESP_WIFI_REMOTE_ENABLED) + default y if SOC_WIFI_SUPPORTED + help + Protocol examples can use Wi-Fi and/or Ethernet to connect to the network. + Choose this option to connect with WiFi + + if EXAMPLE_CONNECT_WIFI + config EXAMPLE_WIFI_SSID_PWD_FROM_STDIN + bool "Get ssid and password from stdin" + default n + help + Give the WiFi SSID and password from stdin. + + config EXAMPLE_PROVIDE_WIFI_CONSOLE_CMD + depends on !EXAMPLE_WIFI_SSID_PWD_FROM_STDIN + bool "Provide wifi connect commands" + default y + help + Provide wifi connect commands for esp_console. + Please use `example_register_wifi_connect_commands` to register them. + + config EXAMPLE_WIFI_SSID + depends on !EXAMPLE_WIFI_SSID_PWD_FROM_STDIN + string "WiFi SSID" + default "myssid" + help + SSID (network name) for the example to connect to. + + config EXAMPLE_WIFI_PASSWORD + depends on !EXAMPLE_WIFI_SSID_PWD_FROM_STDIN + string "WiFi Password" + default "mypassword" + help + WiFi password (WPA or WPA2) for the example to use. + Can be left blank if the network has no security set. + + config EXAMPLE_WIFI_CONN_MAX_RETRY + int "Maximum retry" + default 6 + help + Set the Maximum retry to avoid station reconnecting to the AP unlimited, + in case the AP is really inexistent. + + choice EXAMPLE_WIFI_SCAN_METHOD + prompt "WiFi Scan Method" + default EXAMPLE_WIFI_SCAN_METHOD_ALL_CHANNEL + help + WiFi scan method: + + If "Fast" is selected, scan will end after find SSID match AP. + + If "All Channel" is selected, scan will end after scan all the channel. + + config EXAMPLE_WIFI_SCAN_METHOD_FAST + bool "Fast" + config EXAMPLE_WIFI_SCAN_METHOD_ALL_CHANNEL + bool "All Channel" + endchoice + + menu "WiFi Scan threshold" + config EXAMPLE_WIFI_SCAN_RSSI_THRESHOLD + int "WiFi minimum rssi" + range -127 0 + + default -127 + help + The minimum rssi to accept in the scan mode. + + choice EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD + prompt "WiFi Scan auth mode threshold" + default EXAMPLE_WIFI_AUTH_OPEN + help + The weakest authmode to accept in the scan mode. + + config EXAMPLE_WIFI_AUTH_OPEN + bool "OPEN" + config EXAMPLE_WIFI_AUTH_WEP + bool "WEP" + config EXAMPLE_WIFI_AUTH_WPA_PSK + bool "WPA PSK" + config EXAMPLE_WIFI_AUTH_WPA2_PSK + bool "WPA2 PSK" + config EXAMPLE_WIFI_AUTH_WPA_WPA2_PSK + bool "WPA WPA2 PSK" + config EXAMPLE_WIFI_AUTH_WPA2_ENTERPRISE + bool "WPA2 ENTERPRISE" + config EXAMPLE_WIFI_AUTH_WPA3_PSK + bool "WPA3 PSK" + config EXAMPLE_WIFI_AUTH_WPA2_WPA3_PSK + bool "WPA2 WPA3 PSK" + config EXAMPLE_WIFI_AUTH_WAPI_PSK + bool "WAPI PSK" + endchoice + endmenu + + choice EXAMPLE_WIFI_CONNECT_AP_SORT_METHOD + prompt "WiFi Connect AP Sort Method" + default EXAMPLE_WIFI_CONNECT_AP_BY_SIGNAL + help + WiFi connect AP sort method: + + If "Signal" is selected, Sort matched APs in scan list by RSSI. + + If "Security" is selected, Sort matched APs in scan list by security mode. + + config EXAMPLE_WIFI_CONNECT_AP_BY_SIGNAL + bool "Signal" + config EXAMPLE_WIFI_CONNECT_AP_BY_SECURITY + bool "Security" + endchoice + endif + + config EXAMPLE_CONNECT_ETHERNET + bool "connect using Ethernet interface" + depends on !IDF_TARGET_LINUX + default y if !EXAMPLE_CONNECT_WIFI + help + Protocol examples can use Wi-Fi and/or Ethernet to connect to the network. + Choose this option to connect with Ethernet + + if EXAMPLE_CONNECT_ETHERNET + config EXAMPLE_ETHERNET_EMAC_TASK_STACK_SIZE + int "emac_rx task stack size" + default 2048 + help + This set stack size for emac_rx task + + config EXAMPLE_USE_SPI_ETHERNET + bool + + choice EXAMPLE_ETHERNET_TYPE + prompt "Ethernet Type" + default EXAMPLE_USE_INTERNAL_ETHERNET if SOC_EMAC_SUPPORTED + default EXAMPLE_USE_W5500 + help + Select which kind of Ethernet will be used in the example. + + config EXAMPLE_USE_INTERNAL_ETHERNET + depends on SOC_EMAC_SUPPORTED + select ETH_USE_ESP32_EMAC + bool "Internal EMAC" + help + Select internal Ethernet MAC controller. + + config EXAMPLE_USE_DM9051 + bool "DM9051 Module" + select EXAMPLE_USE_SPI_ETHERNET + select ETH_USE_SPI_ETHERNET + select ETH_SPI_ETHERNET_DM9051 + help + Select external SPI-Ethernet module. + + config EXAMPLE_USE_W5500 + bool "W5500 Module" + select EXAMPLE_USE_SPI_ETHERNET + select ETH_USE_SPI_ETHERNET + select ETH_SPI_ETHERNET_W5500 + help + Select external SPI-Ethernet module (W5500). + + config EXAMPLE_USE_OPENETH + bool "OpenCores Ethernet MAC (EXPERIMENTAL)" + select ETH_USE_OPENETH + help + When this option is enabled, the example is built with support for + OpenCores Ethernet MAC, which allows testing the example in QEMU. + Note that this option is used for internal testing purposes, and + not officially supported. Examples built with this option enabled + will not run on a real ESP32 chip. + + endchoice # EXAMPLE_ETHERNET_TYPE + + if EXAMPLE_USE_INTERNAL_ETHERNET + choice EXAMPLE_ETH_PHY_MODEL + prompt "Ethernet PHY Device" + default EXAMPLE_ETH_PHY_IP101 + help + Select the Ethernet PHY device to use in the example. + + config EXAMPLE_ETH_PHY_IP101 + bool "IP101" + help + IP101 is a single port 10/100 MII/RMII/TP/Fiber Fast Ethernet Transceiver. + Goto http://www.icplus.com.tw/pp-IP101G.html for more information about it. + + config EXAMPLE_ETH_PHY_RTL8201 + bool "RTL8201/SR8201" + help + RTL8201F/SR8201F is a single port 10/100Mb Ethernet Transceiver with auto MDIX. + Goto http://www.corechip-sz.com/productsview.asp?id=22 for more information about it. + + config EXAMPLE_ETH_PHY_LAN87XX + bool "LAN87xx" + help + Below chips are supported: + LAN8710A is a small footprint MII/RMII 10/100 Ethernet Transceiver with HP Auto-MDIX and + flexPWR® Technology. + LAN8720A is a small footprint RMII 10/100 Ethernet Transceiver with HP Auto-MDIX Support. + LAN8740A/LAN8741A is a small footprint MII/RMII 10/100 Energy Efficient Ethernet Transceiver + with HP Auto-MDIX and flexPWR® Technology. + LAN8742A is a small footprint RMII 10/100 Ethernet Transceiver with HP Auto-MDIX and + flexPWR® Technology. + Goto https://www.microchip.com for more information about them. + + config EXAMPLE_ETH_PHY_DP83848 + bool "DP83848" + help + DP83848 is a single port 10/100Mb/s Ethernet Physical Layer Transceiver. + Goto http://www.ti.com/product/DP83848J for more information about it. + + config EXAMPLE_ETH_PHY_KSZ80XX + bool "KSZ80xx" + help + With the KSZ80xx series, Microchip offers single-chip 10BASE-T/100BASE-TX + Ethernet Physical Layer Transceivers (PHY). + The following chips are supported: KSZ8001, KSZ8021, KSZ8031, KSZ8041, + KSZ8051, KSZ8061, KSZ8081, KSZ8091 + Goto https://www.microchip.com for more information about them. + endchoice + + config EXAMPLE_ETH_MDC_GPIO + int "SMI MDC GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_OUT_RANGE_MAX + default 23 if IDF_TARGET_ESP32 + default 31 if IDF_TARGET_ESP32P4 + help + Set the GPIO number used by SMI MDC. + + config EXAMPLE_ETH_MDIO_GPIO + int "SMI MDIO GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_OUT_RANGE_MAX + default 18 if IDF_TARGET_ESP32 + default 27 if IDF_TARGET_ESP32P4 + help + Set the GPIO number used by SMI MDIO. + endif + + if EXAMPLE_USE_SPI_ETHERNET + config EXAMPLE_ETH_SPI_HOST + int "SPI Host Number" + range 0 2 + default 1 + help + Set the SPI host used to communicate with the SPI Ethernet Controller. + + config EXAMPLE_ETH_SPI_SCLK_GPIO + int "SPI SCLK GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_OUT_RANGE_MAX + default 14 + help + Set the GPIO number used by SPI SCLK. + + config EXAMPLE_ETH_SPI_MOSI_GPIO + int "SPI MOSI GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_OUT_RANGE_MAX + default 13 + help + Set the GPIO number used by SPI MOSI. + + config EXAMPLE_ETH_SPI_MISO_GPIO + int "SPI MISO GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_IN_RANGE_MAX + default 12 + help + Set the GPIO number used by SPI MISO. + + config EXAMPLE_ETH_SPI_CS_GPIO + int "SPI CS GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_OUT_RANGE_MAX + default 15 + help + Set the GPIO number used by SPI CS. + + config EXAMPLE_ETH_SPI_CLOCK_MHZ + int "SPI clock speed (MHz)" + range 5 80 + default 36 + help + Set the clock speed (MHz) of SPI interface. + + config EXAMPLE_ETH_SPI_INT_GPIO + int "Interrupt GPIO number" + range ENV_GPIO_RANGE_MIN ENV_GPIO_IN_RANGE_MAX + default 4 + help + Set the GPIO number used by the SPI Ethernet module interrupt line. + endif # EXAMPLE_USE_SPI_ETHERNET + + config EXAMPLE_ETH_PHY_RST_GPIO + int "PHY Reset GPIO number" + range -1 ENV_GPIO_OUT_RANGE_MAX + default 26 if IDF_TARGET_ESP32P4 + default 5 + help + Set the GPIO number used to reset PHY chip. + Set to -1 to disable PHY chip hardware reset. + + config EXAMPLE_ETH_PHY_ADDR + int "PHY Address" + range 0 31 if EXAMPLE_USE_INTERNAL_ETHERNET + default 1 + help + Set PHY address according your board schematic. + endif # EXAMPLE_CONNECT_ETHERNET + + config EXAMPLE_CONNECT_PPP + bool "connect using Point to Point interface" + select LWIP_PPP_SUPPORT + help + Protocol examples can use PPP connection over serial line. + Choose this option to connect to the ppp server running + on your laptop over a serial line (either UART or USB ACM) + + if EXAMPLE_CONNECT_PPP + choice EXAMPLE_CONNECT_PPP_DEVICE + prompt "Choose PPP device" + default EXAMPLE_CONNECT_PPP_DEVICE_USB + help + Select which peripheral to use to connect to the PPP server. + + config EXAMPLE_CONNECT_PPP_DEVICE_USB + bool "USB" + depends on SOC_USB_OTG_SUPPORTED + select TINYUSB_CDC_ENABLED + help + Use USB ACM device. + + config EXAMPLE_CONNECT_PPP_DEVICE_UART + bool "UART" + help + Use UART. + + endchoice + + menu "UART Configuration" + depends on EXAMPLE_CONNECT_PPP_DEVICE_UART + config EXAMPLE_CONNECT_UART_TX_PIN + int "TXD Pin Number" + default 4 + range 0 31 + help + Pin number of UART TX. + + config EXAMPLE_CONNECT_UART_RX_PIN + int "RXD Pin Number" + default 5 + range 0 31 + help + Pin number of UART RX. + + config EXAMPLE_CONNECT_UART_BAUDRATE + int "UART Baudrate" + default 115200 + range 9600 3000000 + help + Baudrate of the UART device + + endmenu + + config EXAMPLE_PPP_CONN_MAX_RETRY + int "Maximum retry" + default 6 + help + Set the Maximum retry to avoid station reconnecting if the pppd + is not available + + endif # EXAMPLE_CONNECT_PPP + + config EXAMPLE_CONNECT_IPV4 + bool + depends on LWIP_IPV4 + default y + + config EXAMPLE_CONNECT_IPV6 + depends on EXAMPLE_CONNECT_WIFI || EXAMPLE_CONNECT_ETHERNET || EXAMPLE_CONNECT_PPP + bool "Obtain IPv6 address" + default y + select LWIP_IPV6 + select LWIP_PPP_ENABLE_IPV6 if EXAMPLE_CONNECT_PPP + help + By default, examples will wait until IPv4 and IPv6 local link addresses are obtained. + Disable this option if the network does not support IPv6. + Choose the preferred IPv6 address type if the connection code should wait until other than + the local link address gets assigned. + Consider enabling IPv6 stateless address autoconfiguration (SLAAC) in the LWIP component. + + if EXAMPLE_CONNECT_IPV6 + choice EXAMPLE_CONNECT_PREFERRED_IPV6 + prompt "Preferred IPv6 Type" + default EXAMPLE_CONNECT_IPV6_PREF_LOCAL_LINK + help + Select which kind of IPv6 address the connect logic waits for. + + config EXAMPLE_CONNECT_IPV6_PREF_LOCAL_LINK + bool "Local Link Address" + help + Blocks until Local link address assigned. + + config EXAMPLE_CONNECT_IPV6_PREF_GLOBAL + bool "Global Address" + help + Blocks until Global address assigned. + + config EXAMPLE_CONNECT_IPV6_PREF_SITE_LOCAL + bool "Site Local Address" + help + Blocks until Site link address assigned. + + config EXAMPLE_CONNECT_IPV6_PREF_UNIQUE_LOCAL + bool "Unique Local Link Address" + help + Blocks until Unique local address assigned. + + endchoice + + endif + + +endmenu diff --git a/components/protocol_examples_common/README.md b/components/protocol_examples_common/README.md new file mode 100644 index 0000000..f80d6b2 --- /dev/null +++ b/components/protocol_examples_common/README.md @@ -0,0 +1,58 @@ +# protocol_example_connect + +This component implements the most common connection methods for ESP32 boards. It should be used mainly in examples of ESP-IDF to demonstrate functionality of network protocols and other libraries, that need the connection step as a prerequisite. + +## How to use this component + +Choose the preferred interface (WiFi, Ethernet, PPPoS) to connect to the network and configure the interface. + +It is possible to enable multiple interfaces simultaneously making the connection phase to block until all the chosen interfaces acquire IP addresses. +It is also possible to disable all interfaces, skipping the connection phase altogether. + +### WiFi + +Choose WiFi connection method (for chipsets that support it) and configure basic WiFi connection properties: +* WiFi SSID +* WiFI password +* Maximum connection retry (connection would be aborted if it doesn't succeed after specified number of retries) +* WiFi scan method (including RSSI and authorization mode threshold) + + + +### Ethernet + +Choose Ethernet connection if your board supports it. The most common settings is using Espressif Ethernet Kit, which is also the recommended HW for this selection. You can also select an SPI ethernet device (if your chipset doesn't support internal EMAC or if you prefer). It is also possible to use OpenCores Ethernet MAC if you're running the example under QEMU. + +### PPP + +Point to point connection method creates a simple IP tunnel to the counterpart device (running PPP server), typically a Linux machine with pppd service. We currently support only PPP over Serial (using UART or USB CDC). This is useful for simple testing of networking layers, but with some additional configuration on the server side, we could simulate standard model of internet connectivity. The PPP server could be also represented by a cellular modem device with pre-configured connectivity and already switched to PPP mode (this setup is not very flexible though, so we suggest using a standard modem library implementing commands and modes, e.g. [esp_modem](https://components.espressif.com/component/espressif/esp_modem) ). + +> [!Note] +> Note that if you choose USB device, you have to manually add a dependency on `esp_tinyusb` component. This step is necessary to keep the `protocol_example_connect` component simple and dependency free. Please run this command from your project location to add the dependency: +> ```bash +> idf.py add-dependency espressif/esp_tinyusb^1 +> ``` + +#### Setup a PPP server + +Connect the board using UART or USB and note the device name, which would be typically: +* `/dev/ttyACMx` for USB devices +* `/dev/ttyUSBx` for UART devices + +Run the pppd server: + +```bash +sudo pppd /dev/ttyACM0 115200 192.168.11.1:192.168.11.2 ms-dns 8.8.8.8 modem local noauth debug nocrtscts nodetach +ipv6 +``` + +Please update the parameters with the correct serial device, baud rate, IP addresses, DNS server, use `+ipv6` if `EXAMPLE_CONNECT_IPV6=y`. + +#### Connection to outside + +In order to access other network endpoints, we have to configure some IP/translation rules. The easiest method is to setup a masquerade of the PPPD created interface (`ppp0`) to your default networking interface (`${ETH0}`). Here is an example of such rule: + +```bash +sudo iptables -t nat -A POSTROUTING -o ${ETH0} -j MASQUERADE +sudo iptables -A FORWARD -i ${ETH0} -o ppp0 -m state --state RELATED,ESTABLISHED -j ACCEPT +sudo iptables -A FORWARD -i ppp0 -o ${ETH0} -j ACCEPT +``` diff --git a/components/protocol_examples_common/addr_from_stdin.c b/components/protocol_examples_common/addr_from_stdin.c new file mode 100644 index 0000000..e4c94b1 --- /dev/null +++ b/components/protocol_examples_common/addr_from_stdin.c @@ -0,0 +1,69 @@ +#include +#include "esp_system.h" +#include "esp_log.h" +#include "esp_netif.h" +#include "protocol_examples_common.h" + +#include "lwip/sockets.h" +#include +#include + +#define HOST_IP_SIZE 128 + +esp_err_t get_addr_from_stdin(int port, int sock_type, int *ip_protocol, int *addr_family, struct sockaddr_storage *dest_addr) +{ + char host_ip[HOST_IP_SIZE]; + int len; + static bool already_init = false; + + // this function could be called multiple times -> make sure UART init runs only once + if (!already_init) { + example_configure_stdin_stdout(); + already_init = true; + } + + // ignore empty or LF only string (could receive from DUT class) + do { + fgets(host_ip, HOST_IP_SIZE, stdin); + len = strlen(host_ip); + } while (len<=1 && host_ip[0] == '\n'); + host_ip[len - 1] = '\0'; + + struct addrinfo hints, *addr_list, *cur; + memset( &hints, 0, sizeof( hints ) ); + + // run getaddrinfo() to decide on the IP protocol + hints.ai_family = AF_UNSPEC; + hints.ai_socktype = sock_type; + hints.ai_protocol = IPPROTO_TCP; + if( getaddrinfo( host_ip, NULL, &hints, &addr_list ) != 0 ) { + return ESP_FAIL; + } + for( cur = addr_list; cur != NULL; cur = cur->ai_next ) { + memcpy(dest_addr, cur->ai_addr, sizeof(*dest_addr)); +#if CONFIG_EXAMPLE_CONNECT_IPV4 + if (cur->ai_family == AF_INET) { + *ip_protocol = IPPROTO_IP; + *addr_family = AF_INET; + // add port number and return on first IPv4 match + ((struct sockaddr_in*)dest_addr)->sin_port = htons(port); + freeaddrinfo( addr_list ); + return ESP_OK; + } +#endif // IPV4 +#if CONFIG_EXAMPLE_CONNECT_IPV6 + if (cur->ai_family == AF_INET6) { + *ip_protocol = IPPROTO_IPV6; + *addr_family = AF_INET6; + // add port and interface number and return on first IPv6 match + ((struct sockaddr_in6*)dest_addr)->sin6_port = htons(port); + ((struct sockaddr_in6*)dest_addr)->sin6_scope_id = esp_netif_get_netif_impl_index(EXAMPLE_INTERFACE); + freeaddrinfo( addr_list ); + return ESP_OK; + } +#endif // IPV6 + } + // no match found + freeaddrinfo( addr_list ); + return ESP_FAIL; +} diff --git a/components/protocol_examples_common/connect.c b/components/protocol_examples_common/connect.c new file mode 100644 index 0000000..f6aa9bb --- /dev/null +++ b/components/protocol_examples_common/connect.c @@ -0,0 +1,138 @@ +/* + * SPDX-FileCopyrightText: 2022-2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ + +#include +#include "protocol_examples_common.h" +#include "example_common_private.h" +#include "sdkconfig.h" +#include "esp_event.h" +#include "esp_wifi.h" +#include "esp_wifi_default.h" +#include "esp_log.h" +#include "esp_netif.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/event_groups.h" +#include "lwip/err.h" +#include "lwip/sys.h" + +static const char *TAG = "example_common"; + +#if CONFIG_EXAMPLE_CONNECT_IPV6 +/* types of ipv6 addresses to be displayed on ipv6 events */ +const char *example_ipv6_addr_types_to_str[6] = { + "ESP_IP6_ADDR_IS_UNKNOWN", + "ESP_IP6_ADDR_IS_GLOBAL", + "ESP_IP6_ADDR_IS_LINK_LOCAL", + "ESP_IP6_ADDR_IS_SITE_LOCAL", + "ESP_IP6_ADDR_IS_UNIQUE_LOCAL", + "ESP_IP6_ADDR_IS_IPV4_MAPPED_IPV6" +}; +#endif + +/** + * @brief Checks the netif description if it contains specified prefix. + * All netifs created withing common connect component are prefixed with the module TAG, + * so it returns true if the specified netif is owned by this module + */ +bool example_is_our_netif(const char *prefix, esp_netif_t *netif) +{ + return strncmp(prefix, esp_netif_get_desc(netif), strlen(prefix) - 1) == 0; +} + +static bool netif_desc_matches_with(esp_netif_t *netif, void *ctx) +{ + return strcmp(ctx, esp_netif_get_desc(netif)) == 0; +} + +esp_netif_t *get_example_netif_from_desc(const char *desc) +{ + return esp_netif_find_if(netif_desc_matches_with, (void*)desc); +} + +static esp_err_t print_all_ips_tcpip(void* ctx) +{ + const char *prefix = ctx; + // iterate over active interfaces, and print out IPs of "our" netifs + esp_netif_t *netif = NULL; + while ((netif = esp_netif_next_unsafe(netif)) != NULL) { + if (example_is_our_netif(prefix, netif)) { + ESP_LOGI(TAG, "Connected to %s", esp_netif_get_desc(netif)); +#if CONFIG_LWIP_IPV4 + esp_netif_ip_info_t ip; + ESP_ERROR_CHECK(esp_netif_get_ip_info(netif, &ip)); + + ESP_LOGI(TAG, "- IPv4 address: " IPSTR ",", IP2STR(&ip.ip)); +#endif +#if CONFIG_EXAMPLE_CONNECT_IPV6 + esp_ip6_addr_t ip6[MAX_IP6_ADDRS_PER_NETIF]; + int ip6_addrs = esp_netif_get_all_ip6(netif, ip6); + for (int j = 0; j < ip6_addrs; ++j) { + esp_ip6_addr_type_t ipv6_type = esp_netif_ip6_get_addr_type(&(ip6[j])); + ESP_LOGI(TAG, "- IPv6 address: " IPV6STR ", type: %s", IPV62STR(ip6[j]), example_ipv6_addr_types_to_str[ipv6_type]); + } +#endif + } + } + return ESP_OK; +} + +void example_print_all_netif_ips(const char *prefix) +{ + // Print all IPs in TCPIP context to avoid potential races of removing/adding netifs when iterating over the list + esp_netif_tcpip_exec(print_all_ips_tcpip, (void*) prefix); +} + + +esp_err_t example_connect(void) +{ +#if CONFIG_EXAMPLE_CONNECT_ETHERNET + if (example_ethernet_connect() != ESP_OK) { + return ESP_FAIL; + } + ESP_ERROR_CHECK(esp_register_shutdown_handler(&example_ethernet_shutdown)); +#endif +#if CONFIG_EXAMPLE_CONNECT_WIFI + if (example_wifi_connect() != ESP_OK) { + return ESP_FAIL; + } + ESP_ERROR_CHECK(esp_register_shutdown_handler(&example_wifi_shutdown)); +#endif +#if CONFIG_EXAMPLE_CONNECT_PPP + if (example_ppp_connect() != ESP_OK) { + return ESP_FAIL; + } + ESP_ERROR_CHECK(esp_register_shutdown_handler(&example_ppp_shutdown)); +#endif + +#if CONFIG_EXAMPLE_CONNECT_ETHERNET + example_print_all_netif_ips(EXAMPLE_NETIF_DESC_ETH); +#endif + +#if CONFIG_EXAMPLE_CONNECT_WIFI + example_print_all_netif_ips(EXAMPLE_NETIF_DESC_STA); +#endif + +#if CONFIG_EXAMPLE_CONNECT_PPP + example_print_all_netif_ips(EXAMPLE_NETIF_DESC_PPP); +#endif + + return ESP_OK; +} + + +esp_err_t example_disconnect(void) +{ +#if CONFIG_EXAMPLE_CONNECT_ETHERNET + example_ethernet_shutdown(); + ESP_ERROR_CHECK(esp_unregister_shutdown_handler(&example_ethernet_shutdown)); +#endif +#if CONFIG_EXAMPLE_CONNECT_WIFI + example_wifi_shutdown(); + ESP_ERROR_CHECK(esp_unregister_shutdown_handler(&example_wifi_shutdown)); +#endif + return ESP_OK; +} diff --git a/components/protocol_examples_common/console_cmd.c b/components/protocol_examples_common/console_cmd.c new file mode 100644 index 0000000..342a92c --- /dev/null +++ b/components/protocol_examples_common/console_cmd.c @@ -0,0 +1,87 @@ +/* + * SPDX-FileCopyrightText: 2022 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ + + +#include +#include "protocol_examples_common.h" +#include "example_common_private.h" +#include "esp_wifi.h" +#include "esp_log.h" +#include "esp_console.h" +#include "argtable3/argtable3.h" + + +static const char *TAG = "example_console"; + +typedef struct { + struct arg_str *ssid; + struct arg_str *password; + struct arg_int *channel; + struct arg_end *end; +} wifi_connect_args_t; +static wifi_connect_args_t connect_args; + +static int cmd_do_wifi_connect(int argc, char **argv) +{ + int nerrors = arg_parse(argc, argv, (void **) &connect_args); + + if (nerrors != 0) { + arg_print_errors(stderr, connect_args.end, argv[0]); + return 1; + } + + wifi_config_t wifi_config = { + .sta = { + .scan_method = WIFI_ALL_CHANNEL_SCAN, + .sort_method = WIFI_CONNECT_AP_BY_SIGNAL, + }, + }; + if (connect_args.channel->count > 0) { + wifi_config.sta.channel = (uint8_t)(connect_args.channel->ival[0]); + } + const char *ssid = connect_args.ssid->sval[0]; + const char *pass = connect_args.password->sval[0]; + strlcpy((char *) wifi_config.sta.ssid, ssid, sizeof(wifi_config.sta.ssid)); + if (pass) { + strlcpy((char *) wifi_config.sta.password, pass, sizeof(wifi_config.sta.password)); + } + example_wifi_sta_do_connect(wifi_config, false); + return 0; +} + +static int cmd_do_wifi_disconnect(int argc, char **argv) +{ + example_wifi_sta_do_disconnect(); + return 0; +} + +void example_register_wifi_connect_commands(void) +{ + ESP_LOGI(TAG, "Registering WiFi connect commands."); + example_wifi_start(); + + connect_args.ssid = arg_str1(NULL, NULL, "", "SSID of AP"); + connect_args.password = arg_str0(NULL, NULL, "", "password of AP"); + connect_args.channel = arg_int0("n", "channel", "", "channel of AP"); + connect_args.end = arg_end(2); + const esp_console_cmd_t wifi_connect_cmd = { + .command = "wifi_connect", + .help = "WiFi is station mode, join specified soft-AP", + .hint = NULL, + .func = &cmd_do_wifi_connect, + .argtable = &connect_args + }; + ESP_ERROR_CHECK( esp_console_cmd_register(&wifi_connect_cmd) ); + + + const esp_console_cmd_t wifi_disconnect_cmd = { + .command = "wifi_disconnect", + .help = "Do wifi disconnect", + .hint = NULL, + .func = &cmd_do_wifi_disconnect, + }; + ESP_ERROR_CHECK( esp_console_cmd_register(&wifi_disconnect_cmd) ); +} diff --git a/components/protocol_examples_common/eth_connect.c b/components/protocol_examples_common/eth_connect.c new file mode 100644 index 0000000..8e89dbe --- /dev/null +++ b/components/protocol_examples_common/eth_connect.c @@ -0,0 +1,241 @@ +/* + * SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ + +#include +#include "protocol_examples_common.h" +#include "example_common_private.h" +#include "esp_event.h" +#include "esp_eth.h" +#if CONFIG_ETH_USE_SPI_ETHERNET +#include "driver/spi_master.h" +#endif // CONFIG_ETH_USE_SPI_ETHERNET +#include "esp_log.h" +#include "esp_mac.h" +#include "driver/gpio.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/event_groups.h" + + +static const char *TAG = "ethernet_connect"; +static SemaphoreHandle_t s_semph_get_ip_addrs = NULL; +#if CONFIG_EXAMPLE_CONNECT_IPV6 +static SemaphoreHandle_t s_semph_get_ip6_addrs = NULL; +#endif + +static esp_netif_t *eth_start(void); +static void eth_stop(void); + + +/** Event handler for Ethernet events */ + +static void eth_on_got_ip(void *arg, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + ip_event_got_ip_t *event = (ip_event_got_ip_t *)event_data; + if (!example_is_our_netif(EXAMPLE_NETIF_DESC_ETH, event->esp_netif)) { + return; + } + ESP_LOGI(TAG, "Got IPv4 event: Interface \"%s\" address: " IPSTR, esp_netif_get_desc(event->esp_netif), IP2STR(&event->ip_info.ip)); + xSemaphoreGive(s_semph_get_ip_addrs); +} + +#if CONFIG_EXAMPLE_CONNECT_IPV6 + +static void eth_on_got_ipv6(void *arg, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + ip_event_got_ip6_t *event = (ip_event_got_ip6_t *)event_data; + if (!example_is_our_netif(EXAMPLE_NETIF_DESC_ETH, event->esp_netif)) { + return; + } + esp_ip6_addr_type_t ipv6_type = esp_netif_ip6_get_addr_type(&event->ip6_info.ip); + ESP_LOGI(TAG, "Got IPv6 event: Interface \"%s\" address: " IPV6STR ", type: %s", esp_netif_get_desc(event->esp_netif), + IPV62STR(event->ip6_info.ip), example_ipv6_addr_types_to_str[ipv6_type]); + if (ipv6_type == EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE) { + xSemaphoreGive(s_semph_get_ip6_addrs); + } +} + +static void on_eth_event(void *esp_netif, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + switch (event_id) { + case ETHERNET_EVENT_CONNECTED: + ESP_LOGI(TAG, "Ethernet Link Up"); + ESP_ERROR_CHECK(esp_netif_create_ip6_linklocal(esp_netif)); + break; + default: + break; + } +} + +#endif // CONFIG_EXAMPLE_CONNECT_IPV6 + +static esp_eth_handle_t s_eth_handle = NULL; +static esp_eth_mac_t *s_mac = NULL; +static esp_eth_phy_t *s_phy = NULL; +static esp_eth_netif_glue_handle_t s_eth_glue = NULL; + +static esp_netif_t *eth_start(void) +{ + esp_netif_inherent_config_t esp_netif_config = ESP_NETIF_INHERENT_DEFAULT_ETH(); + // Warning: the interface desc is used in tests to capture actual connection details (IP, gw, mask) + esp_netif_config.if_desc = EXAMPLE_NETIF_DESC_ETH; + esp_netif_config.route_prio = 64; + esp_netif_config_t netif_config = { + .base = &esp_netif_config, + .stack = ESP_NETIF_NETSTACK_DEFAULT_ETH + }; + esp_netif_t *netif = esp_netif_new(&netif_config); + assert(netif); + + eth_mac_config_t mac_config = ETH_MAC_DEFAULT_CONFIG(); + mac_config.rx_task_stack_size = CONFIG_EXAMPLE_ETHERNET_EMAC_TASK_STACK_SIZE; + eth_phy_config_t phy_config = ETH_PHY_DEFAULT_CONFIG(); + phy_config.phy_addr = CONFIG_EXAMPLE_ETH_PHY_ADDR; + phy_config.reset_gpio_num = CONFIG_EXAMPLE_ETH_PHY_RST_GPIO; +#if CONFIG_EXAMPLE_USE_INTERNAL_ETHERNET + eth_esp32_emac_config_t esp32_emac_config = ETH_ESP32_EMAC_DEFAULT_CONFIG(); + esp32_emac_config.smi_gpio.mdc_num = CONFIG_EXAMPLE_ETH_MDC_GPIO; + esp32_emac_config.smi_gpio.mdio_num = CONFIG_EXAMPLE_ETH_MDIO_GPIO; + s_mac = esp_eth_mac_new_esp32(&esp32_emac_config, &mac_config); +#if CONFIG_EXAMPLE_ETH_PHY_IP101 + s_phy = esp_eth_phy_new_ip101(&phy_config); +#elif CONFIG_EXAMPLE_ETH_PHY_RTL8201 + s_phy = esp_eth_phy_new_rtl8201(&phy_config); +#elif CONFIG_EXAMPLE_ETH_PHY_LAN87XX + s_phy = esp_eth_phy_new_lan87xx(&phy_config); +#elif CONFIG_EXAMPLE_ETH_PHY_DP83848 + s_phy = esp_eth_phy_new_dp83848(&phy_config); +#elif CONFIG_EXAMPLE_ETH_PHY_KSZ80XX + s_phy = esp_eth_phy_new_ksz80xx(&phy_config); +#endif +#elif CONFIG_EXAMPLE_USE_SPI_ETHERNET + gpio_install_isr_service(0); + spi_bus_config_t buscfg = { + .miso_io_num = CONFIG_EXAMPLE_ETH_SPI_MISO_GPIO, + .mosi_io_num = CONFIG_EXAMPLE_ETH_SPI_MOSI_GPIO, + .sclk_io_num = CONFIG_EXAMPLE_ETH_SPI_SCLK_GPIO, + .quadwp_io_num = -1, + .quadhd_io_num = -1, + }; + ESP_ERROR_CHECK(spi_bus_initialize(CONFIG_EXAMPLE_ETH_SPI_HOST, &buscfg, SPI_DMA_CH_AUTO)); + spi_device_interface_config_t spi_devcfg = { + .mode = 0, + .clock_speed_hz = CONFIG_EXAMPLE_ETH_SPI_CLOCK_MHZ * 1000 * 1000, + .spics_io_num = CONFIG_EXAMPLE_ETH_SPI_CS_GPIO, + .queue_size = 20 + }; +#if CONFIG_EXAMPLE_USE_DM9051 + /* dm9051 ethernet driver is based on spi driver */ + eth_dm9051_config_t dm9051_config = ETH_DM9051_DEFAULT_CONFIG(CONFIG_EXAMPLE_ETH_SPI_HOST, &spi_devcfg); + dm9051_config.int_gpio_num = CONFIG_EXAMPLE_ETH_SPI_INT_GPIO; + s_mac = esp_eth_mac_new_dm9051(&dm9051_config, &mac_config); + s_phy = esp_eth_phy_new_dm9051(&phy_config); +#elif CONFIG_EXAMPLE_USE_W5500 + /* w5500 ethernet driver is based on spi driver */ + eth_w5500_config_t w5500_config = ETH_W5500_DEFAULT_CONFIG(CONFIG_EXAMPLE_ETH_SPI_HOST, &spi_devcfg); + w5500_config.int_gpio_num = CONFIG_EXAMPLE_ETH_SPI_INT_GPIO; + s_mac = esp_eth_mac_new_w5500(&w5500_config, &mac_config); + s_phy = esp_eth_phy_new_w5500(&phy_config); +#endif +#elif CONFIG_EXAMPLE_USE_OPENETH + phy_config.autonego_timeout_ms = 100; + s_mac = esp_eth_mac_new_openeth(&mac_config); + s_phy = esp_eth_phy_new_dp83848(&phy_config); +#endif + + // Install Ethernet driver + esp_eth_config_t config = ETH_DEFAULT_CONFIG(s_mac, s_phy); + ESP_ERROR_CHECK(esp_eth_driver_install(&config, &s_eth_handle)); +#if !CONFIG_EXAMPLE_USE_INTERNAL_ETHERNET + /* The SPI Ethernet module might doesn't have a burned factory MAC address, we cat to set it manually. + We set the ESP_MAC_ETH mac address as the default, if you want to use ESP_MAC_EFUSE_CUSTOM mac address, please enable the + configuration: `ESP_MAC_USE_CUSTOM_MAC_AS_BASE_MAC` + */ + uint8_t eth_mac[6] = {0}; + ESP_ERROR_CHECK(esp_read_mac(eth_mac, ESP_MAC_ETH)); + ESP_ERROR_CHECK(esp_eth_ioctl(s_eth_handle, ETH_CMD_S_MAC_ADDR, eth_mac)); +#endif + // combine driver with netif + s_eth_glue = esp_eth_new_netif_glue(s_eth_handle); + esp_netif_attach(netif, s_eth_glue); + + // Register user defined event handers + ESP_ERROR_CHECK(esp_event_handler_register(IP_EVENT, IP_EVENT_ETH_GOT_IP, ð_on_got_ip, NULL)); +#ifdef CONFIG_EXAMPLE_CONNECT_IPV6 + ESP_ERROR_CHECK(esp_event_handler_register(ETH_EVENT, ETHERNET_EVENT_CONNECTED, &on_eth_event, netif)); + ESP_ERROR_CHECK(esp_event_handler_register(IP_EVENT, IP_EVENT_GOT_IP6, ð_on_got_ipv6, NULL)); +#endif + + esp_eth_start(s_eth_handle); + return netif; +} + +static void eth_stop(void) +{ + esp_netif_t *eth_netif = get_example_netif_from_desc(EXAMPLE_NETIF_DESC_ETH); + ESP_ERROR_CHECK(esp_event_handler_unregister(IP_EVENT, IP_EVENT_ETH_GOT_IP, ð_on_got_ip)); +#if CONFIG_EXAMPLE_CONNECT_IPV6 + ESP_ERROR_CHECK(esp_event_handler_unregister(IP_EVENT, IP_EVENT_GOT_IP6, ð_on_got_ipv6)); + ESP_ERROR_CHECK(esp_event_handler_unregister(ETH_EVENT, ETHERNET_EVENT_CONNECTED, &on_eth_event)); +#endif + ESP_ERROR_CHECK(esp_eth_stop(s_eth_handle)); + ESP_ERROR_CHECK(esp_eth_del_netif_glue(s_eth_glue)); + ESP_ERROR_CHECK(esp_eth_driver_uninstall(s_eth_handle)); + s_eth_handle = NULL; + ESP_ERROR_CHECK(s_phy->del(s_phy)); + ESP_ERROR_CHECK(s_mac->del(s_mac)); + + esp_netif_destroy(eth_netif); +} + +esp_eth_handle_t get_example_eth_handle(void) +{ + return s_eth_handle; +} + +/* tear down connection, release resources */ +void example_ethernet_shutdown(void) +{ + if (s_semph_get_ip_addrs == NULL) { + return; + } + vSemaphoreDelete(s_semph_get_ip_addrs); + s_semph_get_ip_addrs = NULL; +#if CONFIG_EXAMPLE_CONNECT_IPV6 + vSemaphoreDelete(s_semph_get_ip6_addrs); + s_semph_get_ip6_addrs = NULL; +#endif + eth_stop(); +} + +esp_err_t example_ethernet_connect(void) +{ +#if CONFIG_EXAMPLE_CONNECT_IPV4 + s_semph_get_ip_addrs = xSemaphoreCreateBinary(); + if (s_semph_get_ip_addrs == NULL) { + return ESP_ERR_NO_MEM; + } +#endif +#if CONFIG_EXAMPLE_CONNECT_IPV6 + s_semph_get_ip6_addrs = xSemaphoreCreateBinary(); + if (s_semph_get_ip6_addrs == NULL) { + vSemaphoreDelete(s_semph_get_ip_addrs); + return ESP_ERR_NO_MEM; + } +#endif + eth_start(); + ESP_LOGI(TAG, "Waiting for IP(s)."); +#if CONFIG_EXAMPLE_CONNECT_IPV4 + xSemaphoreTake(s_semph_get_ip_addrs, portMAX_DELAY); +#endif +#if CONFIG_EXAMPLE_CONNECT_IPV6 + xSemaphoreTake(s_semph_get_ip6_addrs, portMAX_DELAY); +#endif + return ESP_OK; +} diff --git a/components/protocol_examples_common/include/addr_from_stdin.h b/components/protocol_examples_common/include/addr_from_stdin.h new file mode 100644 index 0000000..827f8c2 --- /dev/null +++ b/components/protocol_examples_common/include/addr_from_stdin.h @@ -0,0 +1,44 @@ +/* Common utilities for socket address input interface: + The API get_addr_from_stdin() is mainly used by socket client examples which read IP address from stdin (if configured). + This option is typically used in the CI, but could be enabled in the project configuration. + In that case this component is used to receive a string that is evaluated and processed to output + socket structures to open a connectio + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. + */ + +#pragma once + +#include "lwip/sys.h" +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief Read and evaluate IP address from stdin + * + * This API reads stdin and parses the input address using getaddrinfo() + * to fill in struct sockaddr_storage (for both IPv4 and IPv6) used to open + * a socket. IP protocol is guessed from the IP address string. + * + * @param[in] port port number of expected connection + * @param[in] sock_type expected protocol: SOCK_STREAM or SOCK_DGRAM + * @param[out] ip_protocol resultant IP protocol: IPPROTO_IP or IPPROTO_IP6 + * @param[out] addr_family resultant address family: AF_INET or AF_INET6 + * @param[out] dest_addr sockaddr_storage structure (for both IPv4 and IPv6) + * @return ESP_OK on success, ESP_FAIL otherwise + */ +esp_err_t get_addr_from_stdin(int port, int sock_type, + int *ip_protocol, + int *addr_family, + struct sockaddr_storage *dest_addr); + +#ifdef __cplusplus +} +#endif diff --git a/components/protocol_examples_common/include/example_common_private.h b/components/protocol_examples_common/include/example_common_private.h new file mode 100644 index 0000000..8a0b880 --- /dev/null +++ b/components/protocol_examples_common/include/example_common_private.h @@ -0,0 +1,56 @@ +/* + * SPDX-FileCopyrightText: 2022-2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ +/* Private Funtions of protocol example common */ + +#pragma once + +#include "esp_err.h" +#include "esp_wifi.h" +#include "sdkconfig.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#if CONFIG_EXAMPLE_CONNECT_IPV6 +#define MAX_IP6_ADDRS_PER_NETIF (5) + +#if defined(CONFIG_EXAMPLE_CONNECT_IPV6_PREF_LOCAL_LINK) +#define EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE ESP_IP6_ADDR_IS_LINK_LOCAL +#elif defined(CONFIG_EXAMPLE_CONNECT_IPV6_PREF_GLOBAL) +#define EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE ESP_IP6_ADDR_IS_GLOBAL +#elif defined(CONFIG_EXAMPLE_CONNECT_IPV6_PREF_SITE_LOCAL) +#define EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE ESP_IP6_ADDR_IS_SITE_LOCAL +#elif defined(CONFIG_EXAMPLE_CONNECT_IPV6_PREF_UNIQUE_LOCAL) +#define EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE ESP_IP6_ADDR_IS_UNIQUE_LOCAL +#endif // if-elif CONFIG_EXAMPLE_CONNECT_IPV6_PREF_... + +#endif + + +#if CONFIG_EXAMPLE_CONNECT_IPV6 +extern const char *example_ipv6_addr_types_to_str[6]; +#endif + +void example_wifi_start(void); +void example_wifi_stop(void); +esp_err_t example_wifi_sta_do_connect(wifi_config_t wifi_config, bool wait); +esp_err_t example_wifi_sta_do_disconnect(void); +bool example_is_our_netif(const char *prefix, esp_netif_t *netif); +void example_print_all_netif_ips(const char *prefix); +void example_wifi_shutdown(void); +esp_err_t example_wifi_connect(void); +void example_ethernet_shutdown(void); +esp_err_t example_ethernet_connect(void); +esp_err_t example_ppp_connect(void); +void example_ppp_start(void); +void example_ppp_shutdown(void); + + + +#ifdef __cplusplus +} +#endif diff --git a/components/protocol_examples_common/include/protocol_examples_common.h b/components/protocol_examples_common/include/protocol_examples_common.h new file mode 100644 index 0000000..b23f452 --- /dev/null +++ b/components/protocol_examples_common/include/protocol_examples_common.h @@ -0,0 +1,147 @@ +/* Common functions for protocol examples, to establish Wi-Fi or Ethernet connection. + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. + */ + +#pragma once + +#include "sdkconfig.h" +#include "esp_err.h" +#if !CONFIG_IDF_TARGET_LINUX +#include "esp_netif.h" +#if CONFIG_EXAMPLE_CONNECT_ETHERNET +#include "esp_eth.h" +#endif +#endif // !CONFIG_IDF_TARGET_LINUX + +#ifdef __cplusplus +extern "C" { +#endif + +#if !CONFIG_IDF_TARGET_LINUX +#if CONFIG_EXAMPLE_CONNECT_WIFI +#define EXAMPLE_NETIF_DESC_STA "example_netif_sta" +#endif + +#if CONFIG_EXAMPLE_CONNECT_ETHERNET +#define EXAMPLE_NETIF_DESC_ETH "example_netif_eth" +#endif + +#if CONFIG_EXAMPLE_CONNECT_PPP +#define EXAMPLE_NETIF_DESC_PPP "example_netif_ppp" +#endif + +#if CONFIG_EXAMPLE_WIFI_SCAN_METHOD_FAST +#define EXAMPLE_WIFI_SCAN_METHOD WIFI_FAST_SCAN +#elif CONFIG_EXAMPLE_WIFI_SCAN_METHOD_ALL_CHANNEL +#define EXAMPLE_WIFI_SCAN_METHOD WIFI_ALL_CHANNEL_SCAN +#endif + +#if CONFIG_EXAMPLE_WIFI_CONNECT_AP_BY_SIGNAL +#define EXAMPLE_WIFI_CONNECT_AP_SORT_METHOD WIFI_CONNECT_AP_BY_SIGNAL +#elif CONFIG_EXAMPLE_WIFI_CONNECT_AP_BY_SECURITY +#define EXAMPLE_WIFI_CONNECT_AP_SORT_METHOD WIFI_CONNECT_AP_BY_SECURITY +#endif + +#if CONFIG_EXAMPLE_WIFI_AUTH_OPEN +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_OPEN +#elif CONFIG_EXAMPLE_WIFI_AUTH_WEP +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WEP +#elif CONFIG_EXAMPLE_WIFI_AUTH_WPA_PSK +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA_PSK +#elif CONFIG_EXAMPLE_WIFI_AUTH_WPA2_PSK +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA2_PSK +#elif CONFIG_EXAMPLE_WIFI_AUTH_WPA_WPA2_PSK +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA_WPA2_PSK +#elif CONFIG_EXAMPLE_WIFI_AUTH_WPA2_ENTERPRISE +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA2_ENTERPRISE +#elif CONFIG_EXAMPLE_WIFI_AUTH_WPA3_PSK +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA3_PSK +#elif CONFIG_EXAMPLE_WIFI_AUTH_WPA2_WPA3_PSK +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA2_WPA3_PSK +#elif CONFIG_EXAMPLE_WIFI_AUTH_WAPI_PSK +#define EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WAPI_PSK +#endif + +/* Example default interface, prefer the ethernet one if running in example-test (CI) configuration */ +#if CONFIG_EXAMPLE_CONNECT_ETHERNET +#define EXAMPLE_INTERFACE get_example_netif_from_desc(EXAMPLE_NETIF_DESC_ETH) +#define get_example_netif() get_example_netif_from_desc(EXAMPLE_NETIF_DESC_ETH) +#elif CONFIG_EXAMPLE_CONNECT_WIFI +#define EXAMPLE_INTERFACE get_example_netif_from_desc(EXAMPLE_NETIF_DESC_STA) +#define get_example_netif() get_example_netif_from_desc(EXAMPLE_NETIF_DESC_STA) +#elif CONFIG_EXAMPLE_CONNECT_PPP +#define EXAMPLE_INTERFACE get_example_netif_from_desc(EXAMPLE_NETIF_DESC_PPP) +#define get_example_netif() get_example_netif_from_desc(EXAMPLE_NETIF_DESC_PPP) +#endif + +/** + * @brief Configure Wi-Fi or Ethernet, connect, wait for IP + * + * This all-in-one helper function is used in protocols examples to + * reduce the amount of boilerplate in the example. + * + * It is not intended to be used in real world applications. + * See examples under examples/wifi/getting_started/ and examples/ethernet/ + * for more complete Wi-Fi or Ethernet initialization code. + * + * Read "Establishing Wi-Fi or Ethernet Connection" section in + * examples/protocols/README.md for more information about this function. + * + * @return ESP_OK on successful connection + */ +esp_err_t example_connect(void); + +/** + * Counterpart to example_connect, de-initializes Wi-Fi or Ethernet + */ +esp_err_t example_disconnect(void); + +/** + * @brief Configure stdin and stdout to use blocking I/O + * + * This helper function is used in ASIO examples. It wraps installing the + * UART driver and configuring VFS layer to use UART driver for console I/O. + */ +esp_err_t example_configure_stdin_stdout(void); + +/** + * @brief Returns esp-netif pointer created by example_connect() described by + * the supplied desc field + * + * @param desc Textual interface of created network interface, for example "sta" + * indicate default WiFi station, "eth" default Ethernet interface. + * + */ +esp_netif_t *get_example_netif_from_desc(const char *desc); + +#if CONFIG_EXAMPLE_PROVIDE_WIFI_CONSOLE_CMD +/** + * @brief Register wifi connect commands + * + * Provide a simple wifi_connect command in esp_console. + * This function can be used after esp_console is initialized. + */ +void example_register_wifi_connect_commands(void); +#endif + +#if CONFIG_EXAMPLE_CONNECT_ETHERNET +/** + * @brief Get the example Ethernet driver handle + * + * @return esp_eth_handle_t + */ +esp_eth_handle_t get_example_eth_handle(void); +#endif // CONFIG_EXAMPLE_CONNECT_ETHERNET + +#else +static inline esp_err_t example_connect(void) {return ESP_OK;} +#endif // !CONFIG_IDF_TARGET_LINUX + +#ifdef __cplusplus +} +#endif diff --git a/components/protocol_examples_common/include/protocol_examples_utils.h b/components/protocol_examples_common/include/protocol_examples_utils.h new file mode 100644 index 0000000..7903117 --- /dev/null +++ b/components/protocol_examples_common/include/protocol_examples_utils.h @@ -0,0 +1,49 @@ +/* + * Utility functions for protocol examples + * + * SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ + +#pragma once + +#include + +#ifdef __cplusplus +extern "C" { +#endif + + +/** + * @brief Encode an URI + * + * @param dest a destination memory location + * @param src the source string + * @param len the length of the source string + * @return uint32_t the count of escaped characters + * + * @note Please allocate the destination buffer keeping in mind that encoding a + * special character will take up 3 bytes (for '%' and two hex digits). + * In the worst-case scenario, the destination buffer will have to be 3 times + * that of the source string. + */ +uint32_t example_uri_encode(char *dest, const char *src, size_t len); + +/** + * @brief Decode an URI + * + * @param dest a destination memory location + * @param src the source string + * @param len the length of the source string + * + * @note Please allocate the destination buffer keeping in mind that a decoded + * special character will take up 2 less bytes than its encoded form. + * In the worst-case scenario, the destination buffer will have to be + * the same size that of the source string. + */ +void example_uri_decode(char *dest, const char *src, size_t len); + +#ifdef __cplusplus +} +#endif diff --git a/components/protocol_examples_common/ppp_connect.c b/components/protocol_examples_common/ppp_connect.c new file mode 100644 index 0000000..090a3ed --- /dev/null +++ b/components/protocol_examples_common/ppp_connect.c @@ -0,0 +1,260 @@ +/* + * SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ + +#include +#include +#include "sdkconfig.h" +#include "protocol_examples_common.h" +#include "example_common_private.h" + +#if CONFIG_EXAMPLE_CONNECT_PPP +#include "esp_log.h" +#include "esp_netif.h" +#include "esp_netif_ppp.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" + +#if CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_USB +#include "tinyusb.h" +#include "tusb_cdc_acm.h" + +static int s_itf; +static uint8_t buf[CONFIG_TINYUSB_CDC_RX_BUFSIZE]; + +#else // DEVICE is UART + +#include "driver/uart.h" +#define BUF_SIZE (1024) +static bool s_stop_task = false; + +#endif // CONNECT_PPP_DEVICE + + +static const char *TAG = "example_connect_ppp"; +static int s_retry_num = 0; +static EventGroupHandle_t s_event_group = NULL; +static esp_netif_t *s_netif; +static const int GOT_IPV4 = BIT0; +static const int CONNECTION_FAILED = BIT1; +#if CONFIG_EXAMPLE_CONNECT_IPV6 +static const int GOT_IPV6 = BIT2; +#define CONNECT_BITS (GOT_IPV4|GOT_IPV6|CONNECTION_FAILED) +#else +#define CONNECT_BITS (GOT_IPV4|CONNECTION_FAILED) +#endif + +static esp_err_t transmit(void *h, void *buffer, size_t len) +{ + ESP_LOG_BUFFER_HEXDUMP(TAG, buffer, len, ESP_LOG_VERBOSE); +#if CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_USB + tinyusb_cdcacm_write_queue(s_itf, buffer, len); + tinyusb_cdcacm_write_flush(s_itf, 0); +#else // DEVICE_UART + uart_write_bytes(UART_NUM_1, buffer, len); +#endif // CONNECT_PPP_DEVICE + return ESP_OK; +} + +static esp_netif_driver_ifconfig_t driver_cfg = { + .handle = (void *)1, // singleton driver, just to != NULL + .transmit = transmit, +}; +const esp_netif_driver_ifconfig_t *ppp_driver_cfg = &driver_cfg; + +static void on_ip_event(void *arg, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + + if (event_id == IP_EVENT_PPP_GOT_IP) { + ip_event_got_ip_t *event = (ip_event_got_ip_t *)event_data; + if (!example_is_our_netif(EXAMPLE_NETIF_DESC_PPP, event->esp_netif)) { + return; + } + esp_netif_t *netif = event->esp_netif; + esp_netif_dns_info_t dns_info; + ESP_LOGI(TAG, "Got IPv4 event: Interface \"%s\" address: " IPSTR, esp_netif_get_desc(event->esp_netif), IP2STR(&event->ip_info.ip)); + esp_netif_get_dns_info(netif, ESP_NETIF_DNS_MAIN, &dns_info); + ESP_LOGI(TAG, "Main DNS server : " IPSTR, IP2STR(&dns_info.ip.u_addr.ip4)); + xEventGroupSetBits(s_event_group, GOT_IPV4); +#if CONFIG_EXAMPLE_CONNECT_IPV6 + } else if (event_id == IP_EVENT_GOT_IP6) { + ip_event_got_ip6_t *event = (ip_event_got_ip6_t *)event_data; + if (!example_is_our_netif(EXAMPLE_NETIF_DESC_PPP, event->esp_netif)) { + return; + } + esp_ip6_addr_type_t ipv6_type = esp_netif_ip6_get_addr_type(&event->ip6_info.ip); + ESP_LOGI(TAG, "Got IPv6 event: Interface \"%s\" address: " IPV6STR ", type: %s", esp_netif_get_desc(event->esp_netif), + IPV62STR(event->ip6_info.ip), example_ipv6_addr_types_to_str[ipv6_type]); + if (ipv6_type == EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE) { + xEventGroupSetBits(s_event_group, GOT_IPV6); + } +#endif + } else if (event_id == IP_EVENT_PPP_LOST_IP) { + ESP_LOGI(TAG, "Disconnect from PPP Server"); + s_retry_num++; + if (s_retry_num > CONFIG_EXAMPLE_PPP_CONN_MAX_RETRY) { + ESP_LOGE(TAG, "PPP Connection failed %d times, stop reconnecting.", s_retry_num); + xEventGroupSetBits(s_event_group, CONNECTION_FAILED); + } else { + ESP_LOGI(TAG, "PPP Connection failed %d times, try to reconnect.", s_retry_num); + esp_netif_action_start(s_netif, 0, 0, 0); + esp_netif_action_connected(s_netif, 0, 0, 0); + } + + } +} + +#if CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_USB +static void cdc_rx_callback(int itf, cdcacm_event_t *event) +{ + size_t rx_size = 0; + if (itf != s_itf) { + // Not our channel + return; + } + esp_err_t ret = tinyusb_cdcacm_read(itf, buf, CONFIG_TINYUSB_CDC_RX_BUFSIZE, &rx_size); + if (ret == ESP_OK) { + ESP_LOG_BUFFER_HEXDUMP(TAG, buf, rx_size, ESP_LOG_VERBOSE); + // pass the received data to the network interface + esp_netif_receive(s_netif, buf, rx_size, NULL); + } else { + ESP_LOGE(TAG, "Read error"); + } +} + +static void line_state_changed(int itf, cdcacm_event_t *event) +{ + s_itf = itf; // use this channel for the netif communication + ESP_LOGI(TAG, "Line state changed on channel %d", itf); +} +#else // DEVICE is UART + +static void ppp_task(void *args) +{ + uart_config_t uart_config = {}; + uart_config.baud_rate = CONFIG_EXAMPLE_CONNECT_UART_BAUDRATE; + uart_config.data_bits = UART_DATA_8_BITS; + uart_config.parity = UART_PARITY_DISABLE; + uart_config.stop_bits = UART_STOP_BITS_1; + uart_config.flow_ctrl = UART_HW_FLOWCTRL_DISABLE; + uart_config.source_clk = UART_SCLK_DEFAULT; + + QueueHandle_t event_queue; + ESP_ERROR_CHECK(uart_driver_install(UART_NUM_1, BUF_SIZE, 0, 16, &event_queue, 0)); + ESP_ERROR_CHECK(uart_param_config(UART_NUM_1, &uart_config)); + ESP_ERROR_CHECK(uart_set_pin(UART_NUM_1, CONFIG_EXAMPLE_CONNECT_UART_TX_PIN, CONFIG_EXAMPLE_CONNECT_UART_RX_PIN, UART_PIN_NO_CHANGE, UART_PIN_NO_CHANGE)); + ESP_ERROR_CHECK(uart_set_rx_timeout(UART_NUM_1, 1)); + + char *buffer = (char*)malloc(BUF_SIZE); + uart_event_t event; + esp_event_handler_register(IP_EVENT, IP_EVENT_PPP_GOT_IP, esp_netif_action_connected, s_netif); + esp_netif_action_start(s_netif, 0, 0, 0); + esp_netif_action_connected(s_netif, 0, 0, 0); + while (!s_stop_task) { + xQueueReceive(event_queue, &event, pdMS_TO_TICKS(1000)); + if (event.type == UART_DATA) { + size_t len; + uart_get_buffered_data_len(UART_NUM_1, &len); + if (len) { + len = uart_read_bytes(UART_NUM_1, buffer, BUF_SIZE, 0); + ESP_LOG_BUFFER_HEXDUMP(TAG, buffer, len, ESP_LOG_VERBOSE); + esp_netif_receive(s_netif, buffer, len, NULL); + } + } else { + ESP_LOGW(TAG, "Received UART event: %d", event.type); + } + } + free(buffer); + vTaskDelete(NULL); +} + +#endif // CONNECT_PPP_DEVICE + +esp_err_t example_ppp_connect(void) +{ + ESP_LOGI(TAG, "Start example_connect."); + +#if CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_USB + ESP_LOGI(TAG, "USB initialization"); + const tinyusb_config_t tusb_cfg = { + .device_descriptor = NULL, + .string_descriptor = NULL, + .external_phy = false, + .configuration_descriptor = NULL, + }; + + ESP_ERROR_CHECK(tinyusb_driver_install(&tusb_cfg)); + + tinyusb_config_cdcacm_t acm_cfg = { + .usb_dev = TINYUSB_USBDEV_0, + .cdc_port = TINYUSB_CDC_ACM_0, + .callback_rx = &cdc_rx_callback, + .callback_rx_wanted_char = NULL, + .callback_line_state_changed = NULL, + .callback_line_coding_changed = NULL + }; + + ESP_ERROR_CHECK(tusb_cdc_acm_init(&acm_cfg)); + /* the second way to register a callback */ + ESP_ERROR_CHECK(tinyusb_cdcacm_register_callback( + TINYUSB_CDC_ACM_0, + CDC_EVENT_LINE_STATE_CHANGED, + &line_state_changed)); +#endif // CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_USB + + s_event_group = xEventGroupCreate(); + + ESP_ERROR_CHECK(esp_event_handler_register(IP_EVENT, ESP_EVENT_ANY_ID, on_ip_event, NULL)); + + esp_netif_inherent_config_t base_netif_cfg = ESP_NETIF_INHERENT_DEFAULT_PPP(); + base_netif_cfg.if_desc = EXAMPLE_NETIF_DESC_PPP; + esp_netif_config_t netif_ppp_config = { .base = &base_netif_cfg, + .driver = ppp_driver_cfg, + .stack = ESP_NETIF_NETSTACK_DEFAULT_PPP + }; + + s_netif = esp_netif_new(&netif_ppp_config); + assert(s_netif); +#if CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_USB + esp_netif_action_start(s_netif, 0, 0, 0); + esp_netif_action_connected(s_netif, 0, 0, 0); +#else // DEVICE is UART + s_stop_task = false; + if (xTaskCreate(ppp_task, "ppp connect", 4096, NULL, 5, NULL) != pdTRUE) { + ESP_LOGE(TAG, "Failed to create a ppp connection task"); + return ESP_FAIL; + } +#endif // CONNECT_PPP_DEVICE + + ESP_LOGI(TAG, "Waiting for IP address"); + EventBits_t bits = xEventGroupWaitBits(s_event_group, CONNECT_BITS, pdFALSE, pdFALSE, portMAX_DELAY); + if (bits & CONNECTION_FAILED) { + ESP_LOGE(TAG, "Connection failed!"); + return ESP_FAIL; + } + ESP_LOGI(TAG, "Connected!"); + + return ESP_OK; +} + +void example_ppp_shutdown(void) +{ + ESP_ERROR_CHECK(esp_event_handler_unregister(IP_EVENT, ESP_EVENT_ANY_ID, on_ip_event)); +#if CONFIG_EXAMPLE_CONNECT_PPP_DEVICE_UART + s_stop_task = true; + vTaskDelay(pdMS_TO_TICKS(1000)); // wait for the ppp task to stop +#endif + + esp_netif_action_disconnected(s_netif, 0, 0, 0); + + vEventGroupDelete(s_event_group); + esp_netif_action_stop(s_netif, 0, 0, 0); + esp_netif_destroy(s_netif); + s_netif = NULL; + s_event_group = NULL; +} + +#endif // CONFIG_EXAMPLE_CONNECT_PPP diff --git a/components/protocol_examples_common/protocol_examples_utils.c b/components/protocol_examples_common/protocol_examples_utils.c new file mode 100644 index 0000000..e6e3de5 --- /dev/null +++ b/components/protocol_examples_common/protocol_examples_utils.c @@ -0,0 +1,388 @@ +/* + * Utility functions for protocol examples + * + * SPDX-FileCopyrightText: 2002-2021 Igor Sysoev + * 2011-2022 Nginx, Inc. + * + * SPDX-License-Identifier: BSD-2-Clause + * + * SPDX-FileContributor: 2023 Espressif Systems (Shanghai) CO LTD + */ +/* + * Copyright (C) 2002-2021 Igor Sysoev + * Copyright (C) 2011-2022 Nginx, Inc. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include +#include +#include +#include + +#include "protocol_examples_utils.h" + +/* Type of Escape algorithms to be used */ +#define NGX_ESCAPE_URI (0) +#define NGX_ESCAPE_ARGS (1) +#define NGX_ESCAPE_URI_COMPONENT (2) +#define NGX_ESCAPE_HTML (3) +#define NGX_ESCAPE_REFRESH (4) +#define NGX_ESCAPE_MEMCACHED (5) +#define NGX_ESCAPE_MAIL_AUTH (6) + +/* Type of Unescape algorithms to be used */ +#define NGX_UNESCAPE_URI (1) +#define NGX_UNESCAPE_REDIRECT (2) + + +uintptr_t ngx_escape_uri(u_char *dst, u_char *src, size_t size, unsigned int type) +{ + unsigned int n; + uint32_t *escape; + static u_char hex[] = "0123456789ABCDEF"; + + /* + * Per RFC 3986 only the following chars are allowed in URIs unescaped: + * + * unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~" + * gen-delims = ":" / "/" / "?" / "#" / "[" / "]" / "@" + * sub-delims = "!" / "$" / "&" / "'" / "(" / ")" + * / "*" / "+" / "," / ";" / "=" + * + * And "%" can appear as a part of escaping itself. The following + * characters are not allowed and need to be escaped: %00-%1F, %7F-%FF, + * " ", """, "<", ">", "\", "^", "`", "{", "|", "}". + */ + + /* " ", "#", "%", "?", not allowed */ + + static uint32_t uri[] = { + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + + /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ + 0xd000002d, /* 1101 0000 0000 0000 0000 0000 0010 1101 */ + + /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ + 0x50000000, /* 0101 0000 0000 0000 0000 0000 0000 0000 */ + + /* ~}| {zyx wvut srqp onml kjih gfed cba` */ + 0xb8000001, /* 1011 1000 0000 0000 0000 0000 0000 0001 */ + + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + }; + + /* " ", "#", "%", "&", "+", ";", "?", not allowed */ + + static uint32_t args[] = { + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + + /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ + 0xd800086d, /* 1101 1000 0000 0000 0000 1000 0110 1101 */ + + /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ + 0x50000000, /* 0101 0000 0000 0000 0000 0000 0000 0000 */ + + /* ~}| {zyx wvut srqp onml kjih gfed cba` */ + 0xb8000001, /* 1011 1000 0000 0000 0000 0000 0000 0001 */ + + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + }; + + /* not ALPHA, DIGIT, "-", ".", "_", "~" */ + + static uint32_t uri_component[] = { + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + + /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ + 0xfc009fff, /* 1111 1100 0000 0000 1001 1111 1111 1111 */ + + /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ + 0x78000001, /* 0111 1000 0000 0000 0000 0000 0000 0001 */ + + /* ~}| {zyx wvut srqp onml kjih gfed cba` */ + 0xb8000001, /* 1011 1000 0000 0000 0000 0000 0000 0001 */ + + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + }; + + /* " ", "#", """, "%", "'", not allowed */ + + static uint32_t html[] = { + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + + /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ + 0x500000ad, /* 0101 0000 0000 0000 0000 0000 1010 1101 */ + + /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ + 0x50000000, /* 0101 0000 0000 0000 0000 0000 0000 0000 */ + + /* ~}| {zyx wvut srqp onml kjih gfed cba` */ + 0xb8000001, /* 1011 1000 0000 0000 0000 0000 0000 0001 */ + + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + }; + + /* " ", """, "'", not allowed */ + + static uint32_t refresh[] = { + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + + /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ + 0x50000085, /* 0101 0000 0000 0000 0000 0000 1000 0101 */ + + /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ + 0x50000000, /* 0101 0000 0000 0000 0000 0000 0000 0000 */ + + /* ~}| {zyx wvut srqp onml kjih gfed cba` */ + 0xd8000001, /* 1011 1000 0000 0000 0000 0000 0000 0001 */ + + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + 0xffffffff /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + }; + + /* " ", "%", %00-%1F */ + + static uint32_t memcached[] = { + 0xffffffff, /* 1111 1111 1111 1111 1111 1111 1111 1111 */ + + /* ?>=< ;:98 7654 3210 /.-, +*)( '&%$ #"! */ + 0x00000021, /* 0000 0000 0000 0000 0000 0000 0010 0001 */ + + /* _^]\ [ZYX WVUT SRQP ONML KJIH GFED CBA@ */ + 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ + + /* ~}| {zyx wvut srqp onml kjih gfed cba` */ + 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ + + 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ + 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ + 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ + 0x00000000, /* 0000 0000 0000 0000 0000 0000 0000 0000 */ + }; + + /* mail_auth is the same as memcached */ + + static uint32_t *map[] = + { uri, args, uri_component, html, refresh, memcached, memcached }; + + + escape = map[type]; + + if (dst == NULL) { + + /* find the number of the characters to be escaped */ + + n = 0; + + while (size) { + if (escape[*src >> 5] & (1U << (*src & 0x1f))) { + n++; + } + src++; + size--; + } + + return (uintptr_t) n; + } + + while (size) { + if (escape[*src >> 5] & (1U << (*src & 0x1f))) { + *dst++ = '%'; + *dst++ = hex[*src >> 4]; + *dst++ = hex[*src & 0xf]; + src++; + + } else { + *dst++ = *src++; + } + size--; + } + + return (uintptr_t) dst; +} + + +void ngx_unescape_uri(u_char **dst, u_char **src, size_t size, unsigned int type) +{ + u_char *d, *s, ch, c, decoded; + enum { + sw_usual = 0, + sw_quoted, + sw_quoted_second + } state; + + d = *dst; + s = *src; + + state = 0; + decoded = 0; + + while (size--) { + + ch = *s++; + + switch (state) { + case sw_usual: + if (ch == '?' + && (type & (NGX_UNESCAPE_URI | NGX_UNESCAPE_REDIRECT))) { + *d++ = ch; + goto done; + } + + if (ch == '%') { + state = sw_quoted; + break; + } + + *d++ = ch; + break; + + case sw_quoted: + + if (ch >= '0' && ch <= '9') { + decoded = (u_char) (ch - '0'); + state = sw_quoted_second; + break; + } + + c = (u_char) (ch | 0x20); + if (c >= 'a' && c <= 'f') { + decoded = (u_char) (c - 'a' + 10); + state = sw_quoted_second; + break; + } + + /* the invalid quoted character */ + + state = sw_usual; + + *d++ = ch; + + break; + + case sw_quoted_second: + + state = sw_usual; + + if (ch >= '0' && ch <= '9') { + ch = (u_char) ((decoded << 4) + (ch - '0')); + + if (type & NGX_UNESCAPE_REDIRECT) { + if (ch > '%' && ch < 0x7f) { + *d++ = ch; + break; + } + + *d++ = '%'; *d++ = *(s - 2); *d++ = *(s - 1); + + break; + } + + *d++ = ch; + + break; + } + + c = (u_char) (ch | 0x20); + if (c >= 'a' && c <= 'f') { + ch = (u_char) ((decoded << 4) + (c - 'a') + 10); + + if (type & NGX_UNESCAPE_URI) { + if (ch == '?') { + *d++ = ch; + goto done; + } + + *d++ = ch; + break; + } + + if (type & NGX_UNESCAPE_REDIRECT) { + if (ch == '?') { + *d++ = ch; + goto done; + } + + if (ch > '%' && ch < 0x7f) { + *d++ = ch; + break; + } + + *d++ = '%'; *d++ = *(s - 2); *d++ = *(s - 1); + break; + } + + *d++ = ch; + + break; + } + + /* the invalid quoted character */ + + break; + } + } + +done: + + *dst = d; + *src = s; +} + + +uint32_t example_uri_encode(char *dest, const char *src, size_t len) +{ + if (!src || !dest) { + return 0; + } + + uintptr_t ret = ngx_escape_uri((unsigned char *)dest, (unsigned char *)src, len, NGX_ESCAPE_URI_COMPONENT); + return (uint32_t)(ret - (uintptr_t)dest); +} + + +void example_uri_decode(char *dest, const char *src, size_t len) +{ + if (!src || !dest) { + return; + } + + unsigned char *src_ptr = (unsigned char *)src; + unsigned char *dst_ptr = (unsigned char *)dest; + ngx_unescape_uri(&dst_ptr, &src_ptr, len, NGX_UNESCAPE_URI); +} diff --git a/components/protocol_examples_common/stdin_out.c b/components/protocol_examples_common/stdin_out.c new file mode 100644 index 0000000..9f3a516 --- /dev/null +++ b/components/protocol_examples_common/stdin_out.c @@ -0,0 +1,34 @@ +/* Common functions for protocol examples, to configure stdin and stdout. + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. + */ + +#include "protocol_examples_common.h" +#include "esp_err.h" +#include "driver/uart_vfs.h" +#include "driver/uart.h" +#include "sdkconfig.h" + +esp_err_t example_configure_stdin_stdout(void) +{ + static bool configured = false; + if (configured) { + return ESP_OK; + } + // Initialize VFS & UART so we can use std::cout/cin + setvbuf(stdin, NULL, _IONBF, 0); + /* Install UART driver for interrupt-driven reads and writes */ + ESP_ERROR_CHECK( uart_driver_install( (uart_port_t)CONFIG_ESP_CONSOLE_UART_NUM, + 256, 0, 0, NULL, 0) ); + /* Tell VFS to use UART driver */ + uart_vfs_dev_use_driver(CONFIG_ESP_CONSOLE_UART_NUM); + uart_vfs_dev_port_set_rx_line_endings(CONFIG_ESP_CONSOLE_UART_NUM, ESP_LINE_ENDINGS_CR); + /* Move the caret to the beginning of the next line on '\n' */ + uart_vfs_dev_port_set_tx_line_endings(CONFIG_ESP_CONSOLE_UART_NUM, ESP_LINE_ENDINGS_CRLF); + configured = true; + return ESP_OK; +} diff --git a/components/protocol_examples_common/wifi_connect.c b/components/protocol_examples_common/wifi_connect.c new file mode 100644 index 0000000..ed95bcc --- /dev/null +++ b/components/protocol_examples_common/wifi_connect.c @@ -0,0 +1,246 @@ +/* + * SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ +/* Common functions for protocol examples, to establish Wi-Fi or Ethernet connection. + + This example code is in the Public Domain (or CC0 licensed, at your option.) + + Unless required by applicable law or agreed to in writing, this + software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR + CONDITIONS OF ANY KIND, either express or implied. + */ + +#include +#include "protocol_examples_common.h" +#include "example_common_private.h" +#include "esp_log.h" + +#if CONFIG_EXAMPLE_CONNECT_WIFI + +static const char *TAG = "example_connect"; +static esp_netif_t *s_example_sta_netif = NULL; +static SemaphoreHandle_t s_semph_get_ip_addrs = NULL; +#if CONFIG_EXAMPLE_CONNECT_IPV6 +static SemaphoreHandle_t s_semph_get_ip6_addrs = NULL; +#endif + +static int s_retry_num = 0; + +static void example_handler_on_wifi_disconnect(void *arg, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + s_retry_num++; + if (s_retry_num > CONFIG_EXAMPLE_WIFI_CONN_MAX_RETRY) { + ESP_LOGI(TAG, "WiFi Connect failed %d times, stop reconnect.", s_retry_num); + /* let example_wifi_sta_do_connect() return */ + if (s_semph_get_ip_addrs) { + xSemaphoreGive(s_semph_get_ip_addrs); + } +#if CONFIG_EXAMPLE_CONNECT_IPV6 + if (s_semph_get_ip6_addrs) { + xSemaphoreGive(s_semph_get_ip6_addrs); + } +#endif + example_wifi_sta_do_disconnect(); + return; + } + ESP_LOGI(TAG, "Wi-Fi disconnected, trying to reconnect..."); + esp_err_t err = esp_wifi_connect(); + if (err == ESP_ERR_WIFI_NOT_STARTED) { + return; + } + ESP_ERROR_CHECK(err); +} + +static void example_handler_on_wifi_connect(void *esp_netif, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ +#if CONFIG_EXAMPLE_CONNECT_IPV6 + esp_netif_create_ip6_linklocal(esp_netif); +#endif // CONFIG_EXAMPLE_CONNECT_IPV6 +} + +static void example_handler_on_sta_got_ip(void *arg, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + s_retry_num = 0; + ip_event_got_ip_t *event = (ip_event_got_ip_t *)event_data; + if (!example_is_our_netif(EXAMPLE_NETIF_DESC_STA, event->esp_netif)) { + return; + } + ESP_LOGI(TAG, "Got IPv4 event: Interface \"%s\" address: " IPSTR, esp_netif_get_desc(event->esp_netif), IP2STR(&event->ip_info.ip)); + if (s_semph_get_ip_addrs) { + xSemaphoreGive(s_semph_get_ip_addrs); + } else { + ESP_LOGI(TAG, "- IPv4 address: " IPSTR ",", IP2STR(&event->ip_info.ip)); + } +} + +#if CONFIG_EXAMPLE_CONNECT_IPV6 +static void example_handler_on_sta_got_ipv6(void *arg, esp_event_base_t event_base, + int32_t event_id, void *event_data) +{ + ip_event_got_ip6_t *event = (ip_event_got_ip6_t *)event_data; + if (!example_is_our_netif(EXAMPLE_NETIF_DESC_STA, event->esp_netif)) { + return; + } + esp_ip6_addr_type_t ipv6_type = esp_netif_ip6_get_addr_type(&event->ip6_info.ip); + ESP_LOGI(TAG, "Got IPv6 event: Interface \"%s\" address: " IPV6STR ", type: %s", esp_netif_get_desc(event->esp_netif), + IPV62STR(event->ip6_info.ip), example_ipv6_addr_types_to_str[ipv6_type]); + + if (ipv6_type == EXAMPLE_CONNECT_PREFERRED_IPV6_TYPE) { + if (s_semph_get_ip6_addrs) { + xSemaphoreGive(s_semph_get_ip6_addrs); + } else { + ESP_LOGI(TAG, "- IPv6 address: " IPV6STR ", type: %s", IPV62STR(event->ip6_info.ip), example_ipv6_addr_types_to_str[ipv6_type]); + } + } +} +#endif // CONFIG_EXAMPLE_CONNECT_IPV6 + + +void example_wifi_start(void) +{ + wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT(); + ESP_ERROR_CHECK(esp_wifi_init(&cfg)); + + esp_netif_inherent_config_t esp_netif_config = ESP_NETIF_INHERENT_DEFAULT_WIFI_STA(); + // Warning: the interface desc is used in tests to capture actual connection details (IP, gw, mask) + esp_netif_config.if_desc = EXAMPLE_NETIF_DESC_STA; + esp_netif_config.route_prio = 128; + s_example_sta_netif = esp_netif_create_wifi(WIFI_IF_STA, &esp_netif_config); + esp_wifi_set_default_wifi_sta_handlers(); + + ESP_ERROR_CHECK(esp_wifi_set_storage(WIFI_STORAGE_RAM)); + ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA)); + ESP_ERROR_CHECK(esp_wifi_start()); +} + + +void example_wifi_stop(void) +{ + esp_err_t err = esp_wifi_stop(); + if (err == ESP_ERR_WIFI_NOT_INIT) { + return; + } + ESP_ERROR_CHECK(err); + ESP_ERROR_CHECK(esp_wifi_deinit()); + ESP_ERROR_CHECK(esp_wifi_clear_default_wifi_driver_and_handlers(s_example_sta_netif)); + esp_netif_destroy(s_example_sta_netif); + s_example_sta_netif = NULL; +} + + +esp_err_t example_wifi_sta_do_connect(wifi_config_t wifi_config, bool wait) +{ + if (wait) { + s_semph_get_ip_addrs = xSemaphoreCreateBinary(); + if (s_semph_get_ip_addrs == NULL) { + return ESP_ERR_NO_MEM; + } +#if CONFIG_EXAMPLE_CONNECT_IPV6 + s_semph_get_ip6_addrs = xSemaphoreCreateBinary(); + if (s_semph_get_ip6_addrs == NULL) { + vSemaphoreDelete(s_semph_get_ip_addrs); + return ESP_ERR_NO_MEM; + } +#endif + } + s_retry_num = 0; + ESP_ERROR_CHECK(esp_event_handler_register(WIFI_EVENT, WIFI_EVENT_STA_DISCONNECTED, &example_handler_on_wifi_disconnect, NULL)); + ESP_ERROR_CHECK(esp_event_handler_register(IP_EVENT, IP_EVENT_STA_GOT_IP, &example_handler_on_sta_got_ip, NULL)); + ESP_ERROR_CHECK(esp_event_handler_register(WIFI_EVENT, WIFI_EVENT_STA_CONNECTED, &example_handler_on_wifi_connect, s_example_sta_netif)); +#if CONFIG_EXAMPLE_CONNECT_IPV6 + ESP_ERROR_CHECK(esp_event_handler_register(IP_EVENT, IP_EVENT_GOT_IP6, &example_handler_on_sta_got_ipv6, NULL)); +#endif + + ESP_LOGI(TAG, "Connecting to %s...", wifi_config.sta.ssid); + ESP_ERROR_CHECK(esp_wifi_set_config(WIFI_IF_STA, &wifi_config)); + esp_err_t ret = esp_wifi_connect(); + if (ret != ESP_OK) { + ESP_LOGE(TAG, "WiFi connect failed! ret:%x", ret); + return ret; + } + if (wait) { + ESP_LOGI(TAG, "Waiting for IP(s)"); +#if CONFIG_EXAMPLE_CONNECT_IPV4 + xSemaphoreTake(s_semph_get_ip_addrs, portMAX_DELAY); +#endif +#if CONFIG_EXAMPLE_CONNECT_IPV6 + xSemaphoreTake(s_semph_get_ip6_addrs, portMAX_DELAY); +#endif + if (s_retry_num > CONFIG_EXAMPLE_WIFI_CONN_MAX_RETRY) { + return ESP_FAIL; + } + } + return ESP_OK; +} + +esp_err_t example_wifi_sta_do_disconnect(void) +{ + ESP_ERROR_CHECK(esp_event_handler_unregister(WIFI_EVENT, WIFI_EVENT_STA_DISCONNECTED, &example_handler_on_wifi_disconnect)); + ESP_ERROR_CHECK(esp_event_handler_unregister(IP_EVENT, IP_EVENT_STA_GOT_IP, &example_handler_on_sta_got_ip)); + ESP_ERROR_CHECK(esp_event_handler_unregister(WIFI_EVENT, WIFI_EVENT_STA_CONNECTED, &example_handler_on_wifi_connect)); +#if CONFIG_EXAMPLE_CONNECT_IPV6 + ESP_ERROR_CHECK(esp_event_handler_unregister(IP_EVENT, IP_EVENT_GOT_IP6, &example_handler_on_sta_got_ipv6)); +#endif + if (s_semph_get_ip_addrs) { + vSemaphoreDelete(s_semph_get_ip_addrs); + } +#if CONFIG_EXAMPLE_CONNECT_IPV6 + if (s_semph_get_ip6_addrs) { + vSemaphoreDelete(s_semph_get_ip6_addrs); + } +#endif + return esp_wifi_disconnect(); +} + +void example_wifi_shutdown(void) +{ + example_wifi_sta_do_disconnect(); + example_wifi_stop(); +} + +esp_err_t example_wifi_connect(void) +{ + ESP_LOGI(TAG, "Start example_connect."); + example_wifi_start(); + wifi_config_t wifi_config = { + .sta = { +#if !CONFIG_EXAMPLE_WIFI_SSID_PWD_FROM_STDIN + .ssid = CONFIG_EXAMPLE_WIFI_SSID, + .password = CONFIG_EXAMPLE_WIFI_PASSWORD, +#endif + .scan_method = EXAMPLE_WIFI_SCAN_METHOD, + .sort_method = EXAMPLE_WIFI_CONNECT_AP_SORT_METHOD, + .threshold.rssi = CONFIG_EXAMPLE_WIFI_SCAN_RSSI_THRESHOLD, + .threshold.authmode = EXAMPLE_WIFI_SCAN_AUTH_MODE_THRESHOLD, + }, + }; +#if CONFIG_EXAMPLE_WIFI_SSID_PWD_FROM_STDIN + example_configure_stdin_stdout(); + char buf[sizeof(wifi_config.sta.ssid)+sizeof(wifi_config.sta.password)+2] = {0}; + ESP_LOGI(TAG, "Please input ssid password:"); + fgets(buf, sizeof(buf), stdin); + int len = strlen(buf); + buf[len-1] = '\0'; /* removes '\n' */ + memset(wifi_config.sta.ssid, 0, sizeof(wifi_config.sta.ssid)); + + char *rest = NULL; + char *temp = strtok_r(buf, " ", &rest); + strncpy((char*)wifi_config.sta.ssid, temp, sizeof(wifi_config.sta.ssid)); + memset(wifi_config.sta.password, 0, sizeof(wifi_config.sta.password)); + temp = strtok_r(NULL, " ", &rest); + if (temp) { + strncpy((char*)wifi_config.sta.password, temp, sizeof(wifi_config.sta.password)); + } else { + wifi_config.sta.threshold.authmode = WIFI_AUTH_OPEN; + } +#endif + return example_wifi_sta_do_connect(wifi_config, true); +} + + +#endif /* CONFIG_EXAMPLE_CONNECT_WIFI */ diff --git a/dependencies.lock b/dependencies.lock index 6cd8fb1..0b8dd9e 100644 --- a/dependencies.lock +++ b/dependencies.lock @@ -3,22 +3,24 @@ dependencies: component_hash: 779b4ba2464a3ae85681e4b860caa5fdc35801458c23f3039ee761bae7f442a4 dependencies: - name: idf + registry_url: https://components.espressif.com require: private version: '>=4.4.2' source: - registry_url: https://components.espressif.com/ + registry_url: https://components.espressif.com type: service version: 1.1.2 espressif/esp_lcd_touch_gt911: component_hash: f90c3f82f052d1ccdfd71895a062f396ccc1c90ec69d8a99c483180387230bac dependencies: - - name: espressif/esp_lcd_touch - registry_url: https://components.espressif.com/ - require: public - version: ^1.1.0 - name: idf + registry_url: https://components.espressif.com require: private version: '>=4.4.2' + - name: espressif/esp_lcd_touch + registry_url: https://components.espressif.com + require: public + version: ^1.1.0 source: registry_url: https://components.espressif.com/ type: service @@ -38,10 +40,31 @@ dependencies: registry_url: https://components.espressif.com/ type: service version: 2.3.2 + espressif/esp_websocket_client: + component_hash: 8280960def8af4f84bc58d2d76f55357cd1387775cbc2e0a6b3ca229aa7e209e + dependencies: + - name: idf + require: private + version: '>=5.0' + source: + registry_url: https://components.espressif.com/ + type: service + version: 1.3.0 idf: source: type: idf version: 5.3.1 + joltwallet/littlefs: + component_hash: 362f1f5beb5087b0c60169aff82676d2d0ffc991ead975212b0cba95959181c5 + dependencies: + - name: idf + registry_url: https://components.espressif.com + require: private + version: '>=4.3' + source: + registry_url: https://components.espressif.com/ + type: service + version: 1.14.8 lvgl/lvgl: component_hash: 2409fdc84e9766d2a18afd84b051aef3f838348136cdb1c10ac2e8bcdb012bf6 dependencies: [] @@ -49,11 +72,25 @@ dependencies: registry_url: https://components.espressif.com/ type: service version: 9.2.0 + suda-morris/am2302_rmt: + component_hash: b46dd8c20dee72654e8ea4a43b16e8a93e984a6c10426392a4b8486fed50ca93 + dependencies: + - name: idf + registry_url: https://components.espressif.com + require: private + version: '>=5.0' + source: + registry_url: https://components.espressif.com/ + type: service + version: 1.0.0 direct_dependencies: - espressif/esp_lcd_touch_gt911 - espressif/esp_lvgl_port +- espressif/esp_websocket_client - idf +- joltwallet/littlefs - lvgl/lvgl -manifest_hash: b5600105e7af98260d4afd2580596fd962c4f216e9d70b5059131b98ee207d7d +- suda-morris/am2302_rmt +manifest_hash: eea83fb930d30dd687c0634cc1b3ac9d374a209e476f634357cee6bd38fc6b59 target: esp32s3 version: 2.0.0 diff --git a/gdbinit b/gdbinit index 12b61f3..3973b3d 100644 --- a/gdbinit +++ b/gdbinit @@ -1,6 +1,6 @@ -target remote :3333 -set remote hardware-watchpoint-limit 2 -mon reset halt -maintenance flush register-cache -thb app_main +target remote :3333 +set remote hardware-watchpoint-limit 2 +mon reset halt +maintenance flush register-cache +thb app_main c \ No newline at end of file diff --git a/main/CMakeLists.txt b/main/CMakeLists.txt index 348fe82..47d3039 100644 --- a/main/CMakeLists.txt +++ b/main/CMakeLists.txt @@ -1,89 +1,22 @@ -idf_component_register(SRC_DIRS . fonts - INCLUDE_DIRS "." - REQUIRES heap esp_wifi nvs_flash mqtt meteofrance esp_netif image_downloader fatfs sdmmc vfs littlefs - PRIV_REQUIRES littlefs) - -lvgl_port_create_c_image("images/wifi_ok.png" "images/" "ARGB8888" "NONE") -lvgl_port_create_c_image("images/wifi_ko.png" "images/" "ARGB8888" "NONE") -lvgl_port_create_c_image("images/mqtt_ok.png" "images/" "AUTO" "NONE") -lvgl_port_create_c_image("images/mqtt_ko.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p13bisj.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/esp_logo.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p10j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p10n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p11j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p11n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p12j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p12bisj.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p12n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p13j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p13n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p14bisj.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p14j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p14n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p15j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p15n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p16bisj.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p16j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p16n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p17j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p17n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p18j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p18n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p19j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p19n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p1j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p1n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p20j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p20n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p21j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p21n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p22j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p22n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p23j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p23n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p24j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p24n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p25j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p25n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p26j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p26n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p27j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p27n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p28j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p28n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p29j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p29n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p2j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p2n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p30j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p30n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p31j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p31n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p32j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p32n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p3j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p3n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p4j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p4n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p5bisj.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p5j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p5n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p6j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p6n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p7j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p7n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p8j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p8n.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p9j.png" "images/" "ARGB8888" "NONE") -# lvgl_port_create_c_image("images/p9n.png" "images/" "ARGB8888" "NONE") - -lvgl_port_add_images(${COMPONENT_LIB} "images/") - -littlefs_create_partition_image(littlefs images_meteo FLASH_IN_PROJECT) - - -set_source_files_properties( - PROPERTIES COMPILE_OPTIONS - "-DLV_LVGL_H_INCLUDE_SIMPLE;-Wno-format;-DLV_FONT_CUSTOM_DECLARE LV_FONT_DECLARE(montserrat_medium_12) LV_FONT_DECLARE(montserrat_medium_18) LV_FONT_DECLARE(montserrat_medium_24)" - ) +set(EXTRA_COMPONENT_DIRS ../components) + +idf_component_register(SRC_DIRS . fonts + INCLUDE_DIRS "." + REQUIRES heap esp_wifi nvs_flash mqtt meteofrance esp_netif image_downloader fatfs sdmmc vfs littlefs wifi_logger protocol_examples_common app_update esp_https_ota + PRIV_REQUIRES littlefs + EMBED_TXTFILES ${project_dir}/main/ca_cert.pem) + + +set_source_files_properties( + PROPERTIES COMPILE_OPTIONS + "-DLV_LVGL_H_INCLUDE_SIMPLE;-Wno-format;-DLV_FONT_CUSTOM_DECLARE LV_FONT_DECLARE(montserrat_medium_12) LV_FONT_DECLARE(montserrat_medium_18) LV_FONT_DECLARE(montserrat_medium_24)" + ) + +lvgl_port_create_c_image("images/wifi_ok.png" "images/" "ARGB8888" "NONE") +lvgl_port_create_c_image("images/wifi_ko.png" "images/" "ARGB8888" "NONE") +lvgl_port_create_c_image("images/mqtt_ok.png" "images/" "AUTO" "NONE") +lvgl_port_create_c_image("images/mqtt_ko.png" "images/" "ARGB8888" "NONE") + +lvgl_port_add_images(${COMPONENT_LIB} "images/") + +littlefs_create_partition_image(littlefs images_meteo FLASH_IN_PROJECT) \ No newline at end of file diff --git a/main/Kconfig.projbuild b/main/Kconfig.projbuild index 5f26f13..6908f20 100644 --- a/main/Kconfig.projbuild +++ b/main/Kconfig.projbuild @@ -1,67 +1,67 @@ -menu "Example Configuration" - - config ESP_WIFI_SSID - string "WiFi SSID" - default "myssid" - help - SSID (network name) for the example to connect to. - - config ESP_WIFI_PASSWORD - string "WiFi Password" - default "mypassword" - help - WiFi password (WPA or WPA2) for the example to use. - - choice ESP_WIFI_SAE_MODE - prompt "WPA3 SAE mode selection" - default ESP_WPA3_SAE_PWE_BOTH - help - Select mode for SAE as Hunt and Peck, H2E or both. - config ESP_WPA3_SAE_PWE_HUNT_AND_PECK - bool "HUNT AND PECK" - config ESP_WPA3_SAE_PWE_HASH_TO_ELEMENT - bool "H2E" - config ESP_WPA3_SAE_PWE_BOTH - bool "BOTH" - endchoice - - config ESP_WIFI_PW_ID - string "PASSWORD IDENTIFIER" - depends on ESP_WPA3_SAE_PWE_HASH_TO_ELEMENT|| ESP_WPA3_SAE_PWE_BOTH - default "" - help - password identifier for SAE H2E - - config ESP_MAXIMUM_RETRY - int "Maximum retry" - default 5 - help - Set the Maximum retry to avoid station reconnecting to the AP unlimited when the AP is really inexistent. - - choice ESP_WIFI_SCAN_AUTH_MODE_THRESHOLD - prompt "WiFi Scan auth mode threshold" - default ESP_WIFI_AUTH_WPA2_PSK - help - The weakest authmode to accept in the scan mode. - This value defaults to ESP_WIFI_AUTH_WPA2_PSK incase password is present and ESP_WIFI_AUTH_OPEN is used. - Please select ESP_WIFI_AUTH_WEP/ESP_WIFI_AUTH_WPA_PSK incase AP is operating in WEP/WPA mode. - - config ESP_WIFI_AUTH_OPEN - bool "OPEN" - config ESP_WIFI_AUTH_WEP - bool "WEP" - config ESP_WIFI_AUTH_WPA_PSK - bool "WPA PSK" - config ESP_WIFI_AUTH_WPA2_PSK - bool "WPA2 PSK" - config ESP_WIFI_AUTH_WPA_WPA2_PSK - bool "WPA/WPA2 PSK" - config ESP_WIFI_AUTH_WPA3_PSK - bool "WPA3 PSK" - config ESP_WIFI_AUTH_WPA2_WPA3_PSK - bool "WPA2/WPA3 PSK" - config ESP_WIFI_AUTH_WAPI_PSK - bool "WAPI PSK" - endchoice - -endmenu +menu "Example Configuration" + + config ESP_WIFI_SSID + string "WiFi SSID" + default "myssid" + help + SSID (network name) for the example to connect to. + + config ESP_WIFI_PASSWORD + string "WiFi Password" + default "mypassword" + help + WiFi password (WPA or WPA2) for the example to use. + + choice ESP_WIFI_SAE_MODE + prompt "WPA3 SAE mode selection" + default ESP_WPA3_SAE_PWE_BOTH + help + Select mode for SAE as Hunt and Peck, H2E or both. + config ESP_WPA3_SAE_PWE_HUNT_AND_PECK + bool "HUNT AND PECK" + config ESP_WPA3_SAE_PWE_HASH_TO_ELEMENT + bool "H2E" + config ESP_WPA3_SAE_PWE_BOTH + bool "BOTH" + endchoice + + config ESP_WIFI_PW_ID + string "PASSWORD IDENTIFIER" + depends on ESP_WPA3_SAE_PWE_HASH_TO_ELEMENT|| ESP_WPA3_SAE_PWE_BOTH + default "" + help + password identifier for SAE H2E + + config ESP_MAXIMUM_RETRY + int "Maximum retry" + default 5 + help + Set the Maximum retry to avoid station reconnecting to the AP unlimited when the AP is really inexistent. + + choice ESP_WIFI_SCAN_AUTH_MODE_THRESHOLD + prompt "WiFi Scan auth mode threshold" + default ESP_WIFI_AUTH_WPA2_PSK + help + The weakest authmode to accept in the scan mode. + This value defaults to ESP_WIFI_AUTH_WPA2_PSK incase password is present and ESP_WIFI_AUTH_OPEN is used. + Please select ESP_WIFI_AUTH_WEP/ESP_WIFI_AUTH_WPA_PSK incase AP is operating in WEP/WPA mode. + + config ESP_WIFI_AUTH_OPEN + bool "OPEN" + config ESP_WIFI_AUTH_WEP + bool "WEP" + config ESP_WIFI_AUTH_WPA_PSK + bool "WPA PSK" + config ESP_WIFI_AUTH_WPA2_PSK + bool "WPA2 PSK" + config ESP_WIFI_AUTH_WPA_WPA2_PSK + bool "WPA/WPA2 PSK" + config ESP_WIFI_AUTH_WPA3_PSK + bool "WPA3 PSK" + config ESP_WIFI_AUTH_WPA2_WPA3_PSK + bool "WPA2/WPA3 PSK" + config ESP_WIFI_AUTH_WAPI_PSK + bool "WAPI PSK" + endchoice + +endmenu diff --git a/main/ca_cert.pem b/main/ca_cert.pem new file mode 100644 index 0000000..7eff939 --- /dev/null +++ b/main/ca_cert.pem @@ -0,0 +1,22 @@ +-----BEGIN CERTIFICATE----- +MIIDmTCCAoGgAwIBAgIUd5qKY6blEffPyHQZnmQfxkcCO7AwDQYJKoZIhvcNAQEL +BQAwXDELMAkGA1UEBhMCRlIxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoM +GEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZDEVMBMGA1UEAwwMMTkyLjE2OC4wLjI4 +MB4XDTI0MTExMzE4MjYxOVoXDTI1MTExMzE4MjYxOVowXDELMAkGA1UEBhMCRlIx +EzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoMGEludGVybmV0IFdpZGdpdHMg +UHR5IEx0ZDEVMBMGA1UEAwwMMTkyLjE2OC4wLjI4MIIBIjANBgkqhkiG9w0BAQEF +AAOCAQ8AMIIBCgKCAQEA8lKPcpJ6/FhrI+E8fzR93N/XIfEW7GpFa+KNp+DK9DGS +hHno2yVGXNdUFRQEL/2pL8aiZzZ7xGMubzEIr1dlHrb/PplGRTXCxQWnDJDsOu4w +7TbzjYxDhgMwXhSGuFlMexFBh+W9qcO85l4wNSOhHusyf7XZaPAd3NGmK4XsoeXJ +DSROJLLpvyZM3yt1kuC3GTWSqUe4Ldv+kaAfyW+X/PJ7Tgb6frLGNCs5A0zLhFxb +FS2omnqX6+H2Bjvk3nCQr85zcuIrnXQ+Hy58MayS+dRqPTSNw7RqRVvrGUuQuj5y +/ruAVLjG6F9wTZZFJ8Nk2veuFxIG+8ADpglWoYrokQIDAQABo1MwUTAdBgNVHQ4E +FgQUUa64jnTc+VqWQB93Fp/yPuirm2cwHwYDVR0jBBgwFoAUUa64jnTc+VqWQB93 +Fp/yPuirm2cwDwYDVR0TAQH/BAUwAwEB/zANBgkqhkiG9w0BAQsFAAOCAQEAnqg9 +DeBozovXmwcbDTlTqz1b5LJ3Xz4mhUnEssmlDvvlXMqL1CjeXDKgOXtkWaomTJNO +MfMTmkkKg2lomNe2O84nUyPJnHYle5cbxZXAvbkmsi6R95lXFf5+bHAtU05TFYKc +BWMPB3Vwym9qrAc8G1LPr05LYgrJsQ9xkf0pVR7hrjgu9k6ElNAQSiH4dlyK4b/T +12U4zBawZNv3f6OnKOTq2NuwwzxWSwRRbEGUf0qO6Z8LNsj7yvmp2ImfN1e3a39p ++WmxJkHBzg5LxUon8jtiZLKeAPNlAPvKTs/4umE0LdZnsdlYrNR+kFeMMurxHvfZ +ykxPELUVUWEgv/IRbA== +-----END CERTIFICATE----- diff --git a/main/fatfs.c b/main/fatfs.c index c6d0858..7040681 100644 --- a/main/fatfs.c +++ b/main/fatfs.c @@ -1,18 +1,18 @@ -/** - * @file lv_fs_fatfs.c - * - */ - -/********************* - * INCLUDES - *********************/ -#include "ff.h" - -/********************* - * DEFINES - *********************/ - -/********************** - * TYPEDEFS - **********************/ - +/** + * @file lv_fs_fatfs.c + * + */ + +/********************* + * INCLUDES + *********************/ +#include "ff.h" + +/********************* + * DEFINES + *********************/ + +/********************** + * TYPEDEFS + **********************/ + diff --git a/main/fatfs.h b/main/fatfs.h index 12e025f..f8ed143 100644 --- a/main/fatfs.h +++ b/main/fatfs.h @@ -1,2 +1,2 @@ -void my_fatfs_init(void); -#pragma once +void my_fatfs_init(void); +#pragma once diff --git a/main/fonts/Dockerfile b/main/fonts/Dockerfile index 6de4907..f43b100 100644 --- a/main/fonts/Dockerfile +++ b/main/fonts/Dockerfile @@ -1,2 +1,2 @@ -FROM node:14 -RUN npm i lv_font_conv -g +FROM node:14 +RUN npm i lv_font_conv -g diff --git a/main/fonts/montserrat_medium_12.c b/main/fonts/montserrat_medium_12.c index 0892a30..4d23802 100644 --- a/main/fonts/montserrat_medium_12.c +++ b/main/fonts/montserrat_medium_12.c @@ -1,897 +1,897 @@ -/******************************************************************************* - * Size: 12 px - * Bpp: 4 - * Opts: --bpp 4 --size 12 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°èéêûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz ' --format lvgl -o montserrat_medium_12.c - ******************************************************************************/ - -#ifdef LV_LVGL_H_INCLUDE_SIMPLE -#include "lvgl.h" -#else -#include "lvgl/lvgl.h" -#endif - -#ifndef MONTSERRAT_MEDIUM_12 -#define MONTSERRAT_MEDIUM_12 1 -#endif - -#if MONTSERRAT_MEDIUM_12 - -/*----------------- - * BITMAPS - *----------------*/ - -/*Store the image of the glyphs*/ -static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { - /* U+0020 " " */ - - /* U+0027 "'" */ - 0x3c, 0x3b, 0x3b, 0x15, - - /* U+002E "." */ - 0x2a, 0x4, 0xd0, - - /* U+0030 "0" */ - 0x0, 0x9e, 0xe9, 0x0, 0xa, 0xd4, 0x4d, 0xa0, - 0x1f, 0x20, 0x2, 0xf1, 0x5e, 0x0, 0x0, 0xd5, - 0x6c, 0x0, 0x0, 0xc6, 0x5e, 0x0, 0x0, 0xd5, - 0x1f, 0x20, 0x2, 0xf1, 0xa, 0xd4, 0x4d, 0xa0, - 0x0, 0x9e, 0xe9, 0x0, - - /* U+0031 "1" */ - 0xef, 0xf3, 0x22, 0xf3, 0x0, 0xf3, 0x0, 0xf3, - 0x0, 0xf3, 0x0, 0xf3, 0x0, 0xf3, 0x0, 0xf3, - 0x0, 0xf3, - - /* U+0032 "2" */ - 0x19, 0xef, 0xc2, 0x8, 0xb4, 0x3a, 0xe0, 0x0, - 0x0, 0x2f, 0x10, 0x0, 0x5, 0xe0, 0x0, 0x2, - 0xe5, 0x0, 0x1, 0xd7, 0x0, 0x1, 0xd8, 0x0, - 0x1, 0xda, 0x22, 0x21, 0x8f, 0xff, 0xff, 0x70, - - /* U+0033 "3" */ - 0x9f, 0xff, 0xff, 0x1, 0x22, 0x2d, 0x80, 0x0, - 0x9, 0xb0, 0x0, 0x5, 0xf2, 0x0, 0x0, 0x7c, - 0xf8, 0x0, 0x0, 0x2, 0xf2, 0x0, 0x0, 0xe, - 0x4b, 0x94, 0x39, 0xf1, 0x3b, 0xff, 0xc3, 0x0, - - /* U+0034 "4" */ - 0x0, 0x0, 0x9b, 0x0, 0x0, 0x4, 0xe1, 0x0, - 0x0, 0x1e, 0x50, 0x0, 0x0, 0xaa, 0x0, 0x0, - 0x5, 0xe1, 0xd, 0x40, 0x1e, 0x40, 0xd, 0x40, - 0x8f, 0xff, 0xff, 0xfd, 0x12, 0x22, 0x2e, 0x62, - 0x0, 0x0, 0xe, 0x40, - - /* U+0035 "5" */ - 0xc, 0xff, 0xff, 0x0, 0xe5, 0x22, 0x20, 0xf, - 0x10, 0x0, 0x1, 0xff, 0xeb, 0x30, 0x2, 0x23, - 0x9f, 0x10, 0x0, 0x0, 0xd6, 0x0, 0x0, 0xd, - 0x69, 0xb4, 0x38, 0xf1, 0x2a, 0xef, 0xc4, 0x0, - - /* U+0036 "6" */ - 0x0, 0x6d, 0xfd, 0x50, 0x8, 0xd5, 0x23, 0x20, - 0x1f, 0x20, 0x0, 0x0, 0x4d, 0x6d, 0xea, 0x10, - 0x6f, 0xc4, 0x3c, 0xa0, 0x5f, 0x30, 0x2, 0xf0, - 0x2f, 0x20, 0x2, 0xf0, 0xa, 0xc3, 0x2b, 0xa0, - 0x1, 0xaf, 0xfa, 0x10, - - /* U+0037 "7" */ - 0xaf, 0xff, 0xff, 0xba, 0x92, 0x22, 0xd7, 0x76, - 0x0, 0x3f, 0x10, 0x0, 0xa, 0x90, 0x0, 0x1, - 0xf2, 0x0, 0x0, 0x7c, 0x0, 0x0, 0xe, 0x50, - 0x0, 0x5, 0xe0, 0x0, 0x0, 0xc8, 0x0, 0x0, - - /* U+0038 "8" */ - 0x3, 0xcf, 0xea, 0x10, 0xe, 0x81, 0x2c, 0xa0, - 0x2f, 0x10, 0x5, 0xd0, 0xe, 0x70, 0x1b, 0x90, - 0x6, 0xff, 0xff, 0x20, 0x3f, 0x50, 0x18, 0xe0, - 0x6c, 0x0, 0x0, 0xf2, 0x3f, 0x61, 0x29, 0xe0, - 0x5, 0xcf, 0xfb, 0x20, - - /* U+0039 "9" */ - 0x7, 0xef, 0xc3, 0x6, 0xe3, 0x15, 0xe1, 0x98, - 0x0, 0xb, 0x87, 0xd2, 0x3, 0xfb, 0xa, 0xff, - 0xd9, 0xc0, 0x0, 0x10, 0x8b, 0x0, 0x0, 0xd, - 0x70, 0x62, 0x4b, 0xd0, 0x1c, 0xfe, 0xa1, 0x0, - - /* U+0041 "A" */ - 0x0, 0x0, 0x6f, 0x30, 0x0, 0x0, 0x0, 0xdd, - 0x90, 0x0, 0x0, 0x4, 0xe3, 0xf1, 0x0, 0x0, - 0xb, 0x80, 0xc7, 0x0, 0x0, 0x1f, 0x20, 0x6e, - 0x0, 0x0, 0x8c, 0x0, 0x1f, 0x50, 0x0, 0xef, - 0xee, 0xef, 0xb0, 0x6, 0xe2, 0x11, 0x14, 0xf2, - 0xc, 0x70, 0x0, 0x0, 0xb9, - - /* U+0042 "B" */ - 0xbf, 0xff, 0xfb, 0x20, 0xb7, 0x11, 0x2a, 0xd0, - 0xb7, 0x0, 0x3, 0xf0, 0xb7, 0x0, 0x8, 0xc0, - 0xbf, 0xff, 0xff, 0x50, 0xb8, 0x22, 0x26, 0xf2, - 0xb7, 0x0, 0x0, 0xc7, 0xb7, 0x11, 0x15, 0xf4, - 0xbf, 0xff, 0xfd, 0x60, - - /* U+0043 "C" */ - 0x0, 0x3b, 0xef, 0xb3, 0x0, 0x5f, 0x93, 0x38, - 0xe0, 0xe, 0x60, 0x0, 0x0, 0x4, 0xe0, 0x0, - 0x0, 0x0, 0x6c, 0x0, 0x0, 0x0, 0x4, 0xe0, - 0x0, 0x0, 0x0, 0xe, 0x60, 0x0, 0x0, 0x0, - 0x5f, 0x93, 0x38, 0xe0, 0x0, 0x3b, 0xff, 0xb3, - 0x0, - - /* U+0044 "D" */ - 0xbf, 0xff, 0xea, 0x30, 0xb, 0x82, 0x23, 0x9f, - 0x40, 0xb7, 0x0, 0x0, 0x7e, 0xb, 0x70, 0x0, - 0x0, 0xf3, 0xb7, 0x0, 0x0, 0xe, 0x5b, 0x70, - 0x0, 0x0, 0xf3, 0xb7, 0x0, 0x0, 0x7e, 0xb, - 0x82, 0x23, 0x9f, 0x40, 0xbf, 0xff, 0xeb, 0x30, - 0x0, - - /* U+0045 "E" */ - 0xbf, 0xff, 0xff, 0x3b, 0x82, 0x22, 0x20, 0xb7, - 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xbf, 0xff, - 0xfa, 0xb, 0x82, 0x22, 0x10, 0xb7, 0x0, 0x0, - 0xb, 0x82, 0x22, 0x20, 0xbf, 0xff, 0xff, 0x50, - - /* U+0046 "F" */ - 0xbf, 0xff, 0xff, 0x3b, 0x82, 0x22, 0x20, 0xb7, - 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xbf, 0xff, - 0xfa, 0xb, 0x82, 0x22, 0x10, 0xb7, 0x0, 0x0, - 0xb, 0x70, 0x0, 0x0, 0xb7, 0x0, 0x0, 0x0, - - /* U+0047 "G" */ - 0x0, 0x3b, 0xef, 0xc4, 0x0, 0x5f, 0x94, 0x38, - 0xe1, 0xe, 0x70, 0x0, 0x0, 0x4, 0xe0, 0x0, - 0x0, 0x0, 0x6c, 0x0, 0x0, 0x8, 0x24, 0xe0, - 0x0, 0x0, 0xe3, 0xe, 0x60, 0x0, 0xe, 0x30, - 0x5f, 0x93, 0x37, 0xf3, 0x0, 0x3b, 0xef, 0xc4, - 0x0, - - /* U+0048 "H" */ - 0xb7, 0x0, 0x0, 0xb7, 0xb7, 0x0, 0x0, 0xb7, - 0xb7, 0x0, 0x0, 0xb7, 0xb7, 0x0, 0x0, 0xb7, - 0xbf, 0xff, 0xff, 0xf7, 0xb8, 0x22, 0x22, 0xc7, - 0xb7, 0x0, 0x0, 0xb7, 0xb7, 0x0, 0x0, 0xb7, - 0xb7, 0x0, 0x0, 0xb7, - - /* U+0049 "I" */ - 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, - 0xb7, - - /* U+004A "J" */ - 0x4, 0xff, 0xff, 0x0, 0x22, 0x5f, 0x0, 0x0, - 0x3f, 0x0, 0x0, 0x3f, 0x0, 0x0, 0x3f, 0x0, - 0x0, 0x3f, 0x0, 0x0, 0x4e, 0xd, 0x52, 0xba, - 0x5, 0xdf, 0xb2, - - /* U+004B "K" */ - 0xb7, 0x0, 0x7, 0xd1, 0xb7, 0x0, 0x5e, 0x20, - 0xb7, 0x4, 0xe3, 0x0, 0xb7, 0x3e, 0x40, 0x0, - 0xb9, 0xef, 0x20, 0x0, 0xbf, 0x89, 0xd0, 0x0, - 0xba, 0x0, 0xca, 0x0, 0xb7, 0x0, 0x1e, 0x70, - 0xb7, 0x0, 0x3, 0xf3, - - /* U+004C "L" */ - 0xb7, 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xb7, - 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xb7, 0x0, - 0x0, 0xb, 0x70, 0x0, 0x0, 0xb7, 0x0, 0x0, - 0xb, 0x82, 0x22, 0x20, 0xbf, 0xff, 0xff, 0x0, - - /* U+004D "M" */ - 0xb8, 0x0, 0x0, 0x1, 0xf2, 0xbf, 0x10, 0x0, - 0x9, 0xf3, 0xbe, 0xa0, 0x0, 0x2e, 0xf3, 0xb7, - 0xe3, 0x0, 0xb7, 0xf3, 0xb6, 0x7b, 0x4, 0xd0, - 0xf3, 0xb6, 0xd, 0x4c, 0x50, 0xf3, 0xb6, 0x5, - 0xfc, 0x0, 0xf3, 0xb6, 0x0, 0xb3, 0x0, 0xf3, - 0xb6, 0x0, 0x0, 0x0, 0xf3, - - /* U+004E "N" */ - 0xb9, 0x0, 0x0, 0xb7, 0xbf, 0x50, 0x0, 0xb7, - 0xbc, 0xf2, 0x0, 0xb7, 0xb7, 0xad, 0x0, 0xb7, - 0xb7, 0xd, 0x90, 0xb7, 0xb7, 0x2, 0xf5, 0xb7, - 0xb7, 0x0, 0x6f, 0xd7, 0xb7, 0x0, 0xa, 0xf7, - 0xb7, 0x0, 0x0, 0xd7, - - /* U+004F "O" */ - 0x0, 0x3b, 0xef, 0xb4, 0x0, 0x5, 0xf9, 0x33, - 0x8f, 0x60, 0xe, 0x60, 0x0, 0x5, 0xf1, 0x4e, - 0x0, 0x0, 0x0, 0xd5, 0x6c, 0x0, 0x0, 0x0, - 0xb7, 0x4e, 0x0, 0x0, 0x0, 0xd5, 0xe, 0x60, - 0x0, 0x5, 0xf1, 0x5, 0xf9, 0x33, 0x8f, 0x60, - 0x0, 0x3b, 0xef, 0xb4, 0x0, - - /* U+0050 "P" */ - 0xbf, 0xff, 0xd8, 0x0, 0xb8, 0x22, 0x5d, 0x90, - 0xb7, 0x0, 0x4, 0xe0, 0xb7, 0x0, 0x3, 0xf0, - 0xb7, 0x0, 0x2c, 0xa0, 0xbf, 0xff, 0xfa, 0x10, - 0xb8, 0x22, 0x0, 0x0, 0xb7, 0x0, 0x0, 0x0, - 0xb7, 0x0, 0x0, 0x0, - - /* U+0051 "Q" */ - 0x0, 0x3b, 0xef, 0xb4, 0x0, 0x4, 0xf9, 0x33, - 0x8f, 0x60, 0xe, 0x60, 0x0, 0x5, 0xf1, 0x4e, - 0x0, 0x0, 0x0, 0xd5, 0x6c, 0x0, 0x0, 0x0, - 0xb7, 0x4e, 0x0, 0x0, 0x0, 0xd6, 0xf, 0x60, - 0x0, 0x5, 0xf1, 0x5, 0xf8, 0x32, 0x7f, 0x60, - 0x0, 0x4c, 0xff, 0xc5, 0x0, 0x0, 0x0, 0xc, - 0xb0, 0x28, 0x0, 0x0, 0x1, 0xbf, 0xe5, 0x0, - 0x0, 0x0, 0x0, 0x0, - - /* U+0052 "R" */ - 0xbf, 0xff, 0xd8, 0x0, 0xb8, 0x22, 0x5d, 0x90, - 0xb7, 0x0, 0x4, 0xe0, 0xb7, 0x0, 0x3, 0xf0, - 0xb7, 0x0, 0x1b, 0xb0, 0xbf, 0xff, 0xfb, 0x10, - 0xb8, 0x22, 0xb9, 0x0, 0xb7, 0x0, 0x1f, 0x30, - 0xb7, 0x0, 0x7, 0xd0, - - /* U+0053 "S" */ - 0x3, 0xcf, 0xeb, 0x31, 0xf7, 0x23, 0x74, 0x4e, - 0x0, 0x0, 0x1, 0xf9, 0x20, 0x0, 0x2, 0xbf, - 0xd7, 0x0, 0x0, 0x4, 0xca, 0x0, 0x0, 0x4, - 0xe5, 0xb4, 0x23, 0xbb, 0x8, 0xdf, 0xea, 0x10, - - /* U+0054 "T" */ - 0xff, 0xff, 0xff, 0xf2, 0x23, 0xf3, 0x22, 0x0, - 0x1f, 0x10, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1f, - 0x10, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1f, 0x10, - 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1f, 0x10, 0x0, - - /* U+0055 "U" */ - 0xd6, 0x0, 0x0, 0xe4, 0xd6, 0x0, 0x0, 0xe4, - 0xd6, 0x0, 0x0, 0xe4, 0xd6, 0x0, 0x0, 0xe4, - 0xd6, 0x0, 0x0, 0xe4, 0xc7, 0x0, 0x0, 0xf3, - 0x9a, 0x0, 0x2, 0xf1, 0x2f, 0x83, 0x5d, 0xa0, - 0x4, 0xcf, 0xe8, 0x0, - - /* U+0056 "V" */ - 0xc, 0x70, 0x0, 0x0, 0xd5, 0x6, 0xe0, 0x0, - 0x4, 0xe0, 0x0, 0xf4, 0x0, 0xa, 0x80, 0x0, - 0x9b, 0x0, 0x1f, 0x20, 0x0, 0x2f, 0x20, 0x7b, - 0x0, 0x0, 0xc, 0x80, 0xe4, 0x0, 0x0, 0x5, - 0xe5, 0xe0, 0x0, 0x0, 0x0, 0xee, 0x70, 0x0, - 0x0, 0x0, 0x8f, 0x10, 0x0, - - /* U+0057 "W" */ - 0x7c, 0x0, 0x0, 0xe8, 0x0, 0x2, 0xf0, 0x2f, - 0x10, 0x3, 0xfd, 0x0, 0x7, 0xa0, 0xd, 0x60, - 0x8, 0x9f, 0x20, 0xc, 0x50, 0x8, 0xb0, 0xe, - 0x3b, 0x70, 0x1f, 0x0, 0x3, 0xf0, 0x3e, 0x6, - 0xc0, 0x6b, 0x0, 0x0, 0xe5, 0x89, 0x1, 0xf1, - 0xb6, 0x0, 0x0, 0x9a, 0xd4, 0x0, 0xb7, 0xf1, - 0x0, 0x0, 0x4f, 0xe0, 0x0, 0x6f, 0xc0, 0x0, - 0x0, 0xf, 0xa0, 0x0, 0x1f, 0x70, 0x0, - - /* U+0058 "X" */ - 0x5f, 0x10, 0x0, 0xe5, 0xa, 0xb0, 0x9, 0xa0, - 0x1, 0xe6, 0x4e, 0x10, 0x0, 0x4f, 0xe4, 0x0, - 0x0, 0xd, 0xe0, 0x0, 0x0, 0x7d, 0xd8, 0x0, - 0x2, 0xf3, 0x2f, 0x30, 0xc, 0x80, 0x7, 0xd0, - 0x8d, 0x0, 0x0, 0xc9, - - /* U+0059 "Y" */ - 0xc, 0x80, 0x0, 0xa, 0x80, 0x3f, 0x10, 0x3, - 0xe0, 0x0, 0xaa, 0x0, 0xc6, 0x0, 0x1, 0xf3, - 0x5d, 0x0, 0x0, 0x7, 0xce, 0x40, 0x0, 0x0, - 0xe, 0xb0, 0x0, 0x0, 0x0, 0xb7, 0x0, 0x0, - 0x0, 0xb, 0x70, 0x0, 0x0, 0x0, 0xb7, 0x0, - 0x0, - - /* U+005A "Z" */ - 0x6f, 0xff, 0xff, 0xf5, 0x2, 0x22, 0x29, 0xd0, - 0x0, 0x0, 0x3f, 0x30, 0x0, 0x1, 0xe6, 0x0, - 0x0, 0xb, 0xa0, 0x0, 0x0, 0x8d, 0x0, 0x0, - 0x4, 0xf2, 0x0, 0x0, 0x1e, 0x82, 0x22, 0x21, - 0x7f, 0xff, 0xff, 0xf8, - - /* U+0061 "a" */ - 0x8, 0xdf, 0xc3, 0x0, 0xa4, 0x29, 0xd0, 0x0, - 0x0, 0x1f, 0x10, 0x8d, 0xee, 0xf2, 0x4e, 0x10, - 0xf, 0x24, 0xe0, 0x7, 0xf2, 0x9, 0xed, 0x8f, - 0x20, - - /* U+0062 "b" */ - 0xe4, 0x0, 0x0, 0xe, 0x40, 0x0, 0x0, 0xe4, - 0x0, 0x0, 0xe, 0x7c, 0xfc, 0x40, 0xef, 0x52, - 0x7f, 0x2e, 0x60, 0x0, 0xb8, 0xe4, 0x0, 0x8, - 0xae, 0x60, 0x0, 0xb8, 0xef, 0x52, 0x8f, 0x2e, - 0x6d, 0xfc, 0x40, - - /* U+0063 "c" */ - 0x2, 0xbf, 0xe8, 0x0, 0xda, 0x24, 0xc3, 0x5d, - 0x0, 0x0, 0x7, 0xb0, 0x0, 0x0, 0x5d, 0x0, - 0x0, 0x0, 0xda, 0x24, 0xd3, 0x2, 0xbf, 0xe8, - 0x0, - - /* U+0064 "d" */ - 0x0, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1, 0xf1, - 0x0, 0x0, 0x1, 0xf1, 0x2, 0xbf, 0xd6, 0xf1, - 0xe, 0x92, 0x3d, 0xf1, 0x5d, 0x0, 0x4, 0xf1, - 0x7b, 0x0, 0x1, 0xf1, 0x5d, 0x0, 0x3, 0xf1, - 0xe, 0x91, 0x2d, 0xf1, 0x2, 0xbf, 0xe6, 0xf1, - - /* U+0065 "e" */ - 0x2, 0xbf, 0xd5, 0x0, 0xe8, 0x14, 0xe4, 0x5c, - 0x0, 0x6, 0xb7, 0xfe, 0xee, 0xec, 0x5d, 0x0, - 0x0, 0x0, 0xe9, 0x23, 0xa2, 0x2, 0xbf, 0xe9, - 0x0, - - /* U+0066 "f" */ - 0x1, 0xcf, 0x60, 0x9a, 0x11, 0xb, 0x60, 0xd, - 0xff, 0xf3, 0xb, 0x60, 0x0, 0xb6, 0x0, 0xb, - 0x60, 0x0, 0xb6, 0x0, 0xb, 0x60, 0x0, 0xb6, - 0x0, - - /* U+0067 "g" */ - 0x2, 0xbf, 0xe6, 0xe2, 0xe, 0xa2, 0x3c, 0xf2, - 0x5d, 0x0, 0x2, 0xf2, 0x7b, 0x0, 0x0, 0xf2, - 0x5d, 0x0, 0x2, 0xf2, 0xe, 0xa2, 0x3d, 0xf2, - 0x2, 0xbf, 0xe5, 0xf2, 0x0, 0x0, 0x2, 0xf0, - 0xc, 0x62, 0x3b, 0xa0, 0x6, 0xdf, 0xea, 0x10, - - /* U+0068 "h" */ - 0xe4, 0x0, 0x0, 0xe, 0x40, 0x0, 0x0, 0xe4, - 0x0, 0x0, 0xe, 0x7d, 0xfc, 0x20, 0xee, 0x42, - 0xac, 0xe, 0x60, 0x2, 0xf0, 0xe4, 0x0, 0xf, - 0x1e, 0x40, 0x0, 0xf2, 0xe4, 0x0, 0xf, 0x2e, - 0x40, 0x0, 0xf2, - - /* U+0069 "i" */ - 0xd, 0x40, 0x82, 0x0, 0x0, 0xe4, 0xe, 0x40, - 0xe4, 0xe, 0x40, 0xe4, 0xe, 0x40, 0xe4, - - /* U+006A "j" */ - 0x0, 0xd, 0x50, 0x0, 0x72, 0x0, 0x0, 0x0, - 0x0, 0xd4, 0x0, 0xd, 0x40, 0x0, 0xd4, 0x0, - 0xd, 0x40, 0x0, 0xd4, 0x0, 0xd, 0x40, 0x0, - 0xd4, 0x0, 0xd, 0x40, 0x22, 0xf2, 0xd, 0xf8, - 0x0, - - /* U+006B "k" */ - 0xe4, 0x0, 0x0, 0xe, 0x40, 0x0, 0x0, 0xe4, - 0x0, 0x0, 0xe, 0x40, 0xb, 0xa0, 0xe4, 0xb, - 0xb0, 0xe, 0x4b, 0xc0, 0x0, 0xee, 0xfd, 0x0, - 0xe, 0xc1, 0xd9, 0x0, 0xe4, 0x2, 0xf4, 0xe, - 0x40, 0x6, 0xe1, - - /* U+006C "l" */ - 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, - 0xe4, 0xe4, - - /* U+006D "m" */ - 0xe7, 0xdf, 0xb2, 0x9e, 0xe8, 0xe, 0xd3, 0x2c, - 0xfb, 0x23, 0xe5, 0xe6, 0x0, 0x4f, 0x10, 0x9, - 0x9e, 0x40, 0x3, 0xf0, 0x0, 0x8a, 0xe4, 0x0, - 0x3f, 0x0, 0x8, 0xae, 0x40, 0x3, 0xf0, 0x0, - 0x8a, 0xe4, 0x0, 0x3f, 0x0, 0x8, 0xa0, - - /* U+006E "n" */ - 0xe6, 0xdf, 0xc2, 0xe, 0xe4, 0x1a, 0xc0, 0xe6, - 0x0, 0x1f, 0xe, 0x40, 0x0, 0xf1, 0xe4, 0x0, - 0xf, 0x2e, 0x40, 0x0, 0xf2, 0xe4, 0x0, 0xf, - 0x20, - - /* U+006F "o" */ - 0x2, 0xbf, 0xe8, 0x0, 0xe, 0xa2, 0x3e, 0x80, - 0x5d, 0x0, 0x4, 0xf0, 0x7b, 0x0, 0x1, 0xf1, - 0x5d, 0x0, 0x4, 0xf0, 0xd, 0xa2, 0x3e, 0x80, - 0x2, 0xbf, 0xe8, 0x0, - - /* U+0070 "p" */ - 0xe7, 0xdf, 0xc4, 0xe, 0xf4, 0x16, 0xf2, 0xe6, - 0x0, 0xa, 0x8e, 0x40, 0x0, 0x8a, 0xe7, 0x0, - 0xb, 0x8e, 0xf5, 0x28, 0xf2, 0xe6, 0xcf, 0xc4, - 0xe, 0x40, 0x0, 0x0, 0xe4, 0x0, 0x0, 0xe, - 0x40, 0x0, 0x0, - - /* U+0071 "q" */ - 0x2, 0xbf, 0xd5, 0xf1, 0xe, 0xa2, 0x3e, 0xf1, - 0x5d, 0x0, 0x4, 0xf1, 0x7b, 0x0, 0x1, 0xf1, - 0x5d, 0x0, 0x4, 0xf1, 0xe, 0xa2, 0x3e, 0xf1, - 0x2, 0xbf, 0xd5, 0xf1, 0x0, 0x0, 0x1, 0xf1, - 0x0, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1, 0xf1, - - /* U+0072 "r" */ - 0xe6, 0xd8, 0xee, 0x61, 0xe7, 0x0, 0xe4, 0x0, - 0xe4, 0x0, 0xe4, 0x0, 0xe4, 0x0, - - /* U+0073 "s" */ - 0x9, 0xef, 0xc2, 0x6d, 0x22, 0x61, 0x7d, 0x20, - 0x0, 0x9, 0xfe, 0x91, 0x0, 0x2, 0xc9, 0x56, - 0x22, 0xb8, 0x4c, 0xfe, 0xa0, - - /* U+0074 "t" */ - 0x5, 0x30, 0x0, 0xb6, 0x0, 0xdf, 0xff, 0x30, - 0xb6, 0x0, 0xb, 0x60, 0x0, 0xb6, 0x0, 0xb, - 0x60, 0x0, 0xaa, 0x11, 0x2, 0xdf, 0x60, - - /* U+0075 "u" */ - 0xf3, 0x0, 0x2f, 0xf, 0x30, 0x2, 0xf0, 0xf3, - 0x0, 0x2f, 0xf, 0x30, 0x2, 0xf0, 0xe4, 0x0, - 0x4f, 0xa, 0xb2, 0x2c, 0xf0, 0x1b, 0xfe, 0x6f, - 0x0, - - /* U+0076 "v" */ - 0xd, 0x50, 0x0, 0x98, 0x6, 0xc0, 0x0, 0xf2, - 0x1, 0xf2, 0x6, 0xb0, 0x0, 0xa8, 0xc, 0x50, - 0x0, 0x3e, 0x3e, 0x0, 0x0, 0xd, 0xd8, 0x0, - 0x0, 0x6, 0xf2, 0x0, - - /* U+0077 "w" */ - 0xc5, 0x0, 0x3f, 0x10, 0x7, 0x86, 0xa0, 0x9, - 0xf6, 0x0, 0xd3, 0x1f, 0x0, 0xe7, 0xb0, 0x2d, - 0x0, 0xb5, 0x4c, 0xe, 0x18, 0x80, 0x6, 0xa9, - 0x60, 0xa6, 0xd3, 0x0, 0x1e, 0xe1, 0x4, 0xed, - 0x0, 0x0, 0xbb, 0x0, 0xe, 0x80, 0x0, - - /* U+0078 "x" */ - 0x5d, 0x0, 0x4e, 0x10, 0xa9, 0x1e, 0x40, 0x1, - 0xed, 0x90, 0x0, 0x8, 0xf1, 0x0, 0x2, 0xeb, - 0xa0, 0x0, 0xc7, 0xd, 0x60, 0x7c, 0x0, 0x3f, - 0x20, - - /* U+0079 "y" */ - 0xd, 0x50, 0x0, 0x98, 0x7, 0xb0, 0x0, 0xe2, - 0x1, 0xf2, 0x5, 0xc0, 0x0, 0xa7, 0xb, 0x50, - 0x0, 0x4d, 0x1e, 0x0, 0x0, 0xe, 0xb9, 0x0, - 0x0, 0x8, 0xf3, 0x0, 0x0, 0x5, 0xd0, 0x0, - 0x5, 0x2c, 0x60, 0x0, 0x1c, 0xf9, 0x0, 0x0, - - /* U+007A "z" */ - 0x7f, 0xff, 0xfb, 0x0, 0x2, 0xf3, 0x0, 0xc, - 0x70, 0x0, 0x9c, 0x0, 0x4, 0xe1, 0x0, 0x1e, - 0x50, 0x0, 0x8f, 0xff, 0xfd, - - /* U+00B0 "°" */ - 0x6, 0xb7, 0x3, 0x80, 0x84, 0x64, 0x3, 0x73, - 0x80, 0x84, 0x6, 0xb7, 0x0, - - /* U+00E8 "è" */ - 0x2, 0xd5, 0x0, 0x0, 0x1, 0xc3, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x2b, 0xfd, 0x50, 0xe, 0x81, - 0x4e, 0x45, 0xc0, 0x0, 0x6b, 0x7f, 0xee, 0xee, - 0xc5, 0xd0, 0x0, 0x0, 0xe, 0x92, 0x3a, 0x20, - 0x2b, 0xfe, 0x90, - - /* U+00E9 "é" */ - 0x0, 0x1, 0xe5, 0x0, 0x0, 0xb5, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x2b, 0xfd, 0x50, 0xe, 0x81, - 0x4e, 0x45, 0xc0, 0x0, 0x6b, 0x7f, 0xee, 0xee, - 0xc5, 0xd0, 0x0, 0x0, 0xe, 0x92, 0x3a, 0x20, - 0x2b, 0xfe, 0x90, - - /* U+00EA "ê" */ - 0x0, 0x4f, 0xa0, 0x0, 0x2c, 0x29, 0x60, 0x0, - 0x0, 0x0, 0x0, 0x2b, 0xfd, 0x50, 0xe, 0x81, - 0x4e, 0x45, 0xc0, 0x0, 0x6b, 0x7f, 0xee, 0xee, - 0xc5, 0xd0, 0x0, 0x0, 0xe, 0x92, 0x3a, 0x20, - 0x2b, 0xfe, 0x90, - - /* U+00FB "û" */ - 0x1, 0xdd, 0x10, 0x0, 0xa5, 0x4b, 0x0, 0x0, - 0x0, 0x0, 0xf, 0x30, 0x2, 0xf0, 0xf3, 0x0, - 0x2f, 0xf, 0x30, 0x2, 0xf0, 0xf3, 0x0, 0x2f, - 0xe, 0x40, 0x4, 0xf0, 0xab, 0x22, 0xcf, 0x1, - 0xbf, 0xe6, 0xf0 -}; - - -/*--------------------- - * GLYPH DESCRIPTION - *--------------------*/ - -static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { - {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, - {.bitmap_index = 0, .adv_w = 52, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 0, .adv_w = 40, .box_w = 2, .box_h = 4, .ofs_x = 0, .ofs_y = 5}, - {.bitmap_index = 4, .adv_w = 44, .box_w = 3, .box_h = 2, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 7, .adv_w = 128, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 43, .adv_w = 71, .box_w = 4, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 61, .adv_w = 110, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 93, .adv_w = 110, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 125, .adv_w = 128, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 161, .adv_w = 110, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 193, .adv_w = 118, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 229, .adv_w = 115, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 261, .adv_w = 124, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 297, .adv_w = 118, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 329, .adv_w = 141, .box_w = 10, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 374, .adv_w = 145, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 410, .adv_w = 139, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 451, .adv_w = 159, .box_w = 9, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 492, .adv_w = 129, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 524, .adv_w = 122, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 556, .adv_w = 148, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 597, .adv_w = 156, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 633, .adv_w = 60, .box_w = 2, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 642, .adv_w = 98, .box_w = 6, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 669, .adv_w = 138, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 705, .adv_w = 114, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 737, .adv_w = 183, .box_w = 10, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 782, .adv_w = 156, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 818, .adv_w = 161, .box_w = 10, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 863, .adv_w = 139, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 899, .adv_w = 161, .box_w = 10, .box_h = 12, .ofs_x = 0, .ofs_y = -3}, - {.bitmap_index = 959, .adv_w = 140, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 995, .adv_w = 119, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1027, .adv_w = 113, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1059, .adv_w = 152, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1095, .adv_w = 137, .box_w = 10, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 1140, .adv_w = 216, .box_w = 14, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1203, .adv_w = 129, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1239, .adv_w = 124, .box_w = 9, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 1280, .adv_w = 126, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1316, .adv_w = 115, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1341, .adv_w = 131, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1376, .adv_w = 110, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1401, .adv_w = 131, .box_w = 8, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1441, .adv_w = 118, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1466, .adv_w = 68, .box_w = 5, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1491, .adv_w = 132, .box_w = 8, .box_h = 10, .ofs_x = 0, .ofs_y = -3}, - {.bitmap_index = 1531, .adv_w = 131, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1566, .adv_w = 54, .box_w = 3, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1581, .adv_w = 55, .box_w = 5, .box_h = 13, .ofs_x = -2, .ofs_y = -3}, - {.bitmap_index = 1614, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1649, .adv_w = 54, .box_w = 2, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1659, .adv_w = 203, .box_w = 11, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1698, .adv_w = 131, .box_w = 7, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1723, .adv_w = 122, .box_w = 8, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1751, .adv_w = 131, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = -3}, - {.bitmap_index = 1786, .adv_w = 131, .box_w = 8, .box_h = 10, .ofs_x = 0, .ofs_y = -3}, - {.bitmap_index = 1826, .adv_w = 79, .box_w = 4, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1840, .adv_w = 96, .box_w = 6, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1861, .adv_w = 79, .box_w = 5, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1884, .adv_w = 130, .box_w = 7, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1909, .adv_w = 107, .box_w = 8, .box_h = 7, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 1937, .adv_w = 173, .box_w = 11, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1976, .adv_w = 106, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2001, .adv_w = 107, .box_w = 8, .box_h = 10, .ofs_x = -1, .ofs_y = -3}, - {.bitmap_index = 2041, .adv_w = 100, .box_w = 6, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2062, .adv_w = 80, .box_w = 5, .box_h = 5, .ofs_x = 0, .ofs_y = 5}, - {.bitmap_index = 2075, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2110, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2145, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2180, .adv_w = 130, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0} -}; - -/*--------------------- - * CHARACTER MAPPING - *--------------------*/ - -static const uint16_t unicode_list_0[] = { - 0x0, 0x7, 0xe -}; - -static const uint16_t unicode_list_4[] = { - 0x0, 0x38, 0x39, 0x3a, 0x4b -}; - -/*Collect the unicode lists and glyph_id offsets*/ -static const lv_font_fmt_txt_cmap_t cmaps[] = -{ - { - .range_start = 32, .range_length = 15, .glyph_id_start = 1, - .unicode_list = unicode_list_0, .glyph_id_ofs_list = NULL, .list_length = 3, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - }, - { - .range_start = 48, .range_length = 10, .glyph_id_start = 4, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 65, .range_length = 26, .glyph_id_start = 14, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 97, .range_length = 26, .glyph_id_start = 40, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 176, .range_length = 76, .glyph_id_start = 66, - .unicode_list = unicode_list_4, .glyph_id_ofs_list = NULL, .list_length = 5, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - } -}; - -/*----------------- - * KERNING - *----------------*/ - - -/*Map glyph_ids to kern left classes*/ -static const uint8_t kern_left_class_mapping[] = -{ - 0, 0, 1, 2, 3, 0, 4, 5, - 6, 7, 8, 9, 10, 3, 11, 12, - 13, 14, 15, 16, 17, 18, 18, 19, - 20, 21, 18, 18, 14, 22, 14, 23, - 24, 25, 19, 26, 26, 27, 28, 29, - 30, 31, 32, 33, 34, 35, 36, 30, - 36, 36, 37, 33, 30, 30, 31, 31, - 38, 39, 40, 41, 36, 42, 42, 43, - 42, 44, 45, 34, 34, 34, 36 -}; - -/*Map glyph_ids to kern right classes*/ -static const uint8_t kern_right_class_mapping[] = -{ - 0, 0, 1, 2, 3, 4, 5, 6, - 7, 8, 3, 9, 10, 11, 12, 13, - 14, 13, 13, 13, 14, 13, 13, 15, - 13, 13, 13, 13, 14, 13, 14, 13, - 16, 17, 18, 19, 19, 20, 21, 22, - 23, 24, 25, 25, 25, 0, 25, 24, - 26, 27, 24, 24, 28, 28, 25, 28, - 25, 28, 29, 30, 31, 32, 32, 33, - 32, 34, 35, 25, 25, 25, 31 -}; - -/*Kern values between classes*/ -static const int8_t kern_class_values[] = -{ - 9, -11, 1, 9, 4, 3, -8, 1, - 9, 1, 8, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 4, -11, 0, -2, -2, 2, - 2, -2, 0, -2, 2, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -12, 1, -2, - 0, -1, -1, -2, 0, 0, -1, 0, - 0, -2, 0, 0, -4, 0, -4, 0, - -5, -6, -6, -4, 0, 0, 0, 0, - -2, 0, 0, 2, 0, 1, -2, 0, - 1, 0, 2, -1, 0, 0, 0, -4, - 0, -1, 0, 0, 1, 0, 0, 2, - 0, -1, 0, -2, 0, -3, 0, 0, - 0, -2, 0, 0, 0, 0, 0, -1, - 1, -1, -1, 0, -2, 0, 0, 0, - -1, -1, 0, -2, -2, 0, 0, 1, - 0, 0, 0, 0, -1, 0, -2, -2, - -2, 0, 0, 0, 0, 0, -1, 0, - 0, 0, 0, -1, -2, 0, -3, -6, - 4, 0, -5, -1, -2, 0, -1, -9, - 2, -1, 0, 0, 2, 1, -1, -10, - 0, -10, -2, -17, -1, 5, 0, 2, - 0, 0, 0, 0, 0, 0, -3, -2, - 0, -6, 0, 0, 0, 0, -1, -1, - 0, -1, -2, 0, 0, 0, 0, 0, - -2, 0, -2, 0, -1, -2, -2, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -2, -2, 0, -2, -1, 2, 0, - 0, 0, 0, 0, 0, -1, 0, 0, - 1, 0, 0, 0, 0, -2, 0, -2, - -1, -2, 0, 0, 0, 2, 0, -2, - 0, 0, 0, 0, -2, -3, 0, -4, - 6, -10, -4, 2, 0, -2, -12, -3, - 0, -3, 0, -12, 0, -3, -5, -1, - 0, 0, 1, -1, 2, -1, -7, 0, - -10, -5, -4, -5, -6, -2, -5, 0, - -4, -5, 1, 1, 2, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -1, 0, - 0, -1, 0, -2, 0, -3, -4, -4, - -1, 0, 0, 0, 0, -2, 0, 0, - 0, 0, 1, -1, 0, 0, -8, 6, - -2, -8, 0, 2, -3, 0, -10, -1, - -2, 2, 0, -2, 3, 0, -7, -3, - -7, -6, -8, 0, 0, 0, -1, 0, - 0, 0, -1, -1, -2, -5, -6, 0, - -18, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -2, 0, -1, -2, -3, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, -4, 2, - -1, -1, -5, -2, 0, -2, -2, -3, - 0, -3, 0, -1, -2, -1, -1, -3, - -2, 0, -1, 0, -4, 0, 0, 0, - -4, 0, -3, 0, -3, -3, 2, -3, - -4, 0, -2, -2, -2, 0, 0, 0, - 0, 0, -2, 0, 0, -3, 0, -2, - 0, -4, -5, -6, -2, 0, 0, 0, - 0, 15, 0, 0, 1, 0, 0, -2, - 0, 2, 0, 2, -3, 0, -1, -2, - -6, -1, -1, -1, -1, 0, 0, -1, - 0, 0, 0, 0, -2, -2, -2, 0, - -1, 0, -1, 0, 0, 0, -1, -2, - -1, -2, -2, -2, 0, 8, -2, -2, - 3, 0, 0, -9, -3, 2, -3, 1, - -6, 0, -2, -3, -1, 1, 0, 0, - -3, 0, 0, -4, 0, -3, -2, -3, - -2, -2, 0, -3, 1, -4, -3, 6, - 0, 2, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -1, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, -2, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -3, 0, 0, 0, 0, -2, 0, - 0, -2, -2, 0, 0, 0, 0, 0, - -1, 0, 0, 0, 0, 0, -1, 0, - 0, 0, 0, -4, 4, 0, -1, -9, - 0, 0, -4, -2, -5, 0, -5, 0, - -3, -8, -2, -8, -7, -9, 0, -2, - 0, -4, -2, -1, -2, -3, -5, -3, - -7, -8, -4, -2, 0, 6, -4, -7, - 0, 1, -6, 0, -10, -1, -2, 1, - 0, -2, 0, -1, -12, -2, -10, -2, - -14, 0, 1, 0, -1, 0, 0, 0, - 0, -1, -1, -7, -1, 0, -12, 0, - -5, 0, 0, -1, -3, -6, -2, 0, - -1, 0, -9, -2, 0, -6, 0, -6, - -2, -3, -5, -2, -3, -3, 0, -2, - -4, -2, -4, 0, 1, 0, -1, -6, - 0, 4, 0, 0, 0, 0, 0, -1, - -4, 0, 0, 0, 0, 0, 0, 0, - -2, 0, -2, 0, 0, -4, -2, 0, - -1, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 3, -6, 4, 0, - -2, 0, -1, 2, 0, -2, 0, -2, - 0, 0, 0, 0, 0, -2, 0, 0, - -2, -3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -2, -2, 0, -3, - 2, -6, -4, 8, 3, 2, -17, -1, - 4, -2, 0, -7, 0, -2, -2, -2, - 2, -2, -2, -6, -2, 0, -5, 0, - -11, -2, 6, -2, -7, 1, -2, -6, - -6, -2, 8, 0, -7, -5, 6, 0, - 1, -14, -2, 2, -3, -1, -7, -3, - -4, -3, -3, -2, 0, 0, -4, -4, - -2, -11, 0, -11, -3, 0, -7, -11, - -1, -6, -3, -6, -5, 5, 0, 0, - -6, 2, 0, 0, -10, 0, -2, -4, - -3, -6, -4, -5, 0, -2, -6, -2, - -4, -4, -6, -2, -3, 0, -6, -2, - 0, -2, -4, -4, -5, -5, -7, -2, - -4, 0, -7, -6, 6, -2, 1, -18, - -3, 4, -4, -3, -8, -2, -6, -2, - -3, -2, -2, -4, -6, -1, 0, -12, - 0, -12, -4, 5, -7, -13, -4, -7, - -8, -10, -6, 4, 0, 4, -4, 4, - 0, 0, -6, -1, 0, -1, 0, 0, - 0, -2, 0, 0, 0, 0, 0, -2, - 0, 0, 0, 0, -2, 0, 0, 0, - 0, -1, -1, -2, 0, 0, 0, 0, - 0, 0, -4, -1, 0, 0, 0, -4, - 0, -2, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, -2, 0, - 0, -4, -3, -2, 0, -5, -2, -4, - 0, 0, -5, 0, -2, -2, 0, 0, - 0, 0, -16, -4, -8, -2, -7, 0, - -1, 0, 0, 0, 0, 0, 0, 0, - 0, -3, -3, -2, -3, 0, 4, -1, - -4, -1, -3, -4, 0, -2, -1, -1, - 0, 0, -1, 0, 0, -17, -2, -3, - 0, -4, 0, 0, -1, -2, 0, 0, - 0, 0, 1, 0, -1, -3, -1, 3, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, 0, 0, - 0, 0, 0, -4, 0, 0, -5, -2, - -4, 0, 0, -5, 0, -2, 0, 0, - 0, 0, 0, -19, 0, -4, -7, -10, - 0, -3, 0, 0, 0, 0, 0, 0, - 0, 0, -2, -3, -1, -3, 0, -2, - 2, 9, 3, 4, -5, 2, 8, 2, - 6, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -2, 0, -2, 15, - 8, 15, 0, 0, 0, 2, 0, 0, - 7, 0, 0, 0, -1, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -3, -16, -2, -2, -8, -9, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 2, -2, 2, - 3, 2, -6, 0, 0, -2, 2, 0, - 0, 0, 0, 0, -5, 0, -2, -1, - -4, 0, -2, 0, -4, -1, 0, -1, - -3, 0, -2, -5, -4, -2, 0, 0, - 0, 0, -1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -3, -16, - -2, -2, -8, -9, 0, 0, 0, 0, - 0, 10, 0, 0, 0, 0, 0, 0, - 0, 0, 0, -2, 1, -1, 1, -1, - -5, 0, 4, 0, 2, -8, -2, -5, - 0, -3, -7, -4, -5, -8, -7, 0, - -2, -1, -2, -1, 0, -1, -1, 3, - 0, 3, -1, 0, 6, 0, 0, 0, - -1, -2, -2, 0, 0, -5, 0, -1, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -2, -2, 0, -2, - 0, 2, -3, -4, -1, 0, -6, -1, - -4, -1, -2, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -3, 0, 0, 0, 0, -2, 0, -2, - 0, 0, -1, 0, -6, 1, 2, 2, - 0, -5, 1, 3, 1, 6, -5, 0, - -1, 0, -1, -8, 0, 0, -6, -5, - 0, -3, 0, -3, 0, -3, 0, -1, - 3, 0, -2, -6, -2, 7, 0, 0, - -2, 2, 0, 0, -6, 0, -1, -1, - 0, 0, 0, -2, 0, -2, -8, -2, - -4, 0, -6, 0, -2, 0, -3, 0, - 1, 0, -2, 0, -2, -6, 0, -2, - 2, 0, 1, 0, -2, -1, 0, -2, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -2, 0, 0, 0, 0, 0, 0, - -2, -2, 0, 0, 4, -12, 1, 8, - 6, 3, -8, 1, 8, 0, 7, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0 -}; - - -/*Collect the kern class' data in one place*/ -static const lv_font_fmt_txt_kern_classes_t kern_classes = -{ - .class_pair_values = kern_class_values, - .left_class_mapping = kern_left_class_mapping, - .right_class_mapping = kern_right_class_mapping, - .left_class_cnt = 45, - .right_class_cnt = 35, -}; - -/*-------------------- - * ALL CUSTOM DATA - *--------------------*/ - -#if LVGL_VERSION_MAJOR == 8 -/*Store all the custom data of the font*/ -static lv_font_fmt_txt_glyph_cache_t cache; -#endif - -#if LVGL_VERSION_MAJOR >= 8 -static const lv_font_fmt_txt_dsc_t font_dsc = { -#else -static lv_font_fmt_txt_dsc_t font_dsc = { -#endif - .glyph_bitmap = glyph_bitmap, - .glyph_dsc = glyph_dsc, - .cmaps = cmaps, - .kern_dsc = &kern_classes, - .kern_scale = 16, - .cmap_num = 5, - .bpp = 4, - .kern_classes = 1, - .bitmap_format = 0, -#if LVGL_VERSION_MAJOR == 8 - .cache = &cache -#endif -}; - - - -/*----------------- - * PUBLIC FONT - *----------------*/ - -/*Initialize a public general font descriptor*/ -#if LVGL_VERSION_MAJOR >= 8 -const lv_font_t montserrat_medium_12 = { -#else -lv_font_t montserrat_medium_12 = { -#endif - .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ - .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ - .line_height = 13, /*The maximum line height required by the font*/ - .base_line = 3, /*Baseline measured from the bottom of the line*/ -#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) - .subpx = LV_FONT_SUBPX_NONE, -#endif -#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 - .underline_position = -1, - .underline_thickness = 1, -#endif - .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ -#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 - .fallback = NULL, -#endif - .user_data = NULL, -}; - - - -#endif /*#if MONTSERRAT_MEDIUM_12*/ - +/******************************************************************************* + * Size: 12 px + * Bpp: 4 + * Opts: --bpp 4 --size 12 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°èéêûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz ' --format lvgl -o montserrat_medium_12.c + ******************************************************************************/ + +#ifdef LV_LVGL_H_INCLUDE_SIMPLE +#include "lvgl.h" +#else +#include "lvgl/lvgl.h" +#endif + +#ifndef MONTSERRAT_MEDIUM_12 +#define MONTSERRAT_MEDIUM_12 1 +#endif + +#if MONTSERRAT_MEDIUM_12 + +/*----------------- + * BITMAPS + *----------------*/ + +/*Store the image of the glyphs*/ +static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { + /* U+0020 " " */ + + /* U+0027 "'" */ + 0x3c, 0x3b, 0x3b, 0x15, + + /* U+002E "." */ + 0x2a, 0x4, 0xd0, + + /* U+0030 "0" */ + 0x0, 0x9e, 0xe9, 0x0, 0xa, 0xd4, 0x4d, 0xa0, + 0x1f, 0x20, 0x2, 0xf1, 0x5e, 0x0, 0x0, 0xd5, + 0x6c, 0x0, 0x0, 0xc6, 0x5e, 0x0, 0x0, 0xd5, + 0x1f, 0x20, 0x2, 0xf1, 0xa, 0xd4, 0x4d, 0xa0, + 0x0, 0x9e, 0xe9, 0x0, + + /* U+0031 "1" */ + 0xef, 0xf3, 0x22, 0xf3, 0x0, 0xf3, 0x0, 0xf3, + 0x0, 0xf3, 0x0, 0xf3, 0x0, 0xf3, 0x0, 0xf3, + 0x0, 0xf3, + + /* U+0032 "2" */ + 0x19, 0xef, 0xc2, 0x8, 0xb4, 0x3a, 0xe0, 0x0, + 0x0, 0x2f, 0x10, 0x0, 0x5, 0xe0, 0x0, 0x2, + 0xe5, 0x0, 0x1, 0xd7, 0x0, 0x1, 0xd8, 0x0, + 0x1, 0xda, 0x22, 0x21, 0x8f, 0xff, 0xff, 0x70, + + /* U+0033 "3" */ + 0x9f, 0xff, 0xff, 0x1, 0x22, 0x2d, 0x80, 0x0, + 0x9, 0xb0, 0x0, 0x5, 0xf2, 0x0, 0x0, 0x7c, + 0xf8, 0x0, 0x0, 0x2, 0xf2, 0x0, 0x0, 0xe, + 0x4b, 0x94, 0x39, 0xf1, 0x3b, 0xff, 0xc3, 0x0, + + /* U+0034 "4" */ + 0x0, 0x0, 0x9b, 0x0, 0x0, 0x4, 0xe1, 0x0, + 0x0, 0x1e, 0x50, 0x0, 0x0, 0xaa, 0x0, 0x0, + 0x5, 0xe1, 0xd, 0x40, 0x1e, 0x40, 0xd, 0x40, + 0x8f, 0xff, 0xff, 0xfd, 0x12, 0x22, 0x2e, 0x62, + 0x0, 0x0, 0xe, 0x40, + + /* U+0035 "5" */ + 0xc, 0xff, 0xff, 0x0, 0xe5, 0x22, 0x20, 0xf, + 0x10, 0x0, 0x1, 0xff, 0xeb, 0x30, 0x2, 0x23, + 0x9f, 0x10, 0x0, 0x0, 0xd6, 0x0, 0x0, 0xd, + 0x69, 0xb4, 0x38, 0xf1, 0x2a, 0xef, 0xc4, 0x0, + + /* U+0036 "6" */ + 0x0, 0x6d, 0xfd, 0x50, 0x8, 0xd5, 0x23, 0x20, + 0x1f, 0x20, 0x0, 0x0, 0x4d, 0x6d, 0xea, 0x10, + 0x6f, 0xc4, 0x3c, 0xa0, 0x5f, 0x30, 0x2, 0xf0, + 0x2f, 0x20, 0x2, 0xf0, 0xa, 0xc3, 0x2b, 0xa0, + 0x1, 0xaf, 0xfa, 0x10, + + /* U+0037 "7" */ + 0xaf, 0xff, 0xff, 0xba, 0x92, 0x22, 0xd7, 0x76, + 0x0, 0x3f, 0x10, 0x0, 0xa, 0x90, 0x0, 0x1, + 0xf2, 0x0, 0x0, 0x7c, 0x0, 0x0, 0xe, 0x50, + 0x0, 0x5, 0xe0, 0x0, 0x0, 0xc8, 0x0, 0x0, + + /* U+0038 "8" */ + 0x3, 0xcf, 0xea, 0x10, 0xe, 0x81, 0x2c, 0xa0, + 0x2f, 0x10, 0x5, 0xd0, 0xe, 0x70, 0x1b, 0x90, + 0x6, 0xff, 0xff, 0x20, 0x3f, 0x50, 0x18, 0xe0, + 0x6c, 0x0, 0x0, 0xf2, 0x3f, 0x61, 0x29, 0xe0, + 0x5, 0xcf, 0xfb, 0x20, + + /* U+0039 "9" */ + 0x7, 0xef, 0xc3, 0x6, 0xe3, 0x15, 0xe1, 0x98, + 0x0, 0xb, 0x87, 0xd2, 0x3, 0xfb, 0xa, 0xff, + 0xd9, 0xc0, 0x0, 0x10, 0x8b, 0x0, 0x0, 0xd, + 0x70, 0x62, 0x4b, 0xd0, 0x1c, 0xfe, 0xa1, 0x0, + + /* U+0041 "A" */ + 0x0, 0x0, 0x6f, 0x30, 0x0, 0x0, 0x0, 0xdd, + 0x90, 0x0, 0x0, 0x4, 0xe3, 0xf1, 0x0, 0x0, + 0xb, 0x80, 0xc7, 0x0, 0x0, 0x1f, 0x20, 0x6e, + 0x0, 0x0, 0x8c, 0x0, 0x1f, 0x50, 0x0, 0xef, + 0xee, 0xef, 0xb0, 0x6, 0xe2, 0x11, 0x14, 0xf2, + 0xc, 0x70, 0x0, 0x0, 0xb9, + + /* U+0042 "B" */ + 0xbf, 0xff, 0xfb, 0x20, 0xb7, 0x11, 0x2a, 0xd0, + 0xb7, 0x0, 0x3, 0xf0, 0xb7, 0x0, 0x8, 0xc0, + 0xbf, 0xff, 0xff, 0x50, 0xb8, 0x22, 0x26, 0xf2, + 0xb7, 0x0, 0x0, 0xc7, 0xb7, 0x11, 0x15, 0xf4, + 0xbf, 0xff, 0xfd, 0x60, + + /* U+0043 "C" */ + 0x0, 0x3b, 0xef, 0xb3, 0x0, 0x5f, 0x93, 0x38, + 0xe0, 0xe, 0x60, 0x0, 0x0, 0x4, 0xe0, 0x0, + 0x0, 0x0, 0x6c, 0x0, 0x0, 0x0, 0x4, 0xe0, + 0x0, 0x0, 0x0, 0xe, 0x60, 0x0, 0x0, 0x0, + 0x5f, 0x93, 0x38, 0xe0, 0x0, 0x3b, 0xff, 0xb3, + 0x0, + + /* U+0044 "D" */ + 0xbf, 0xff, 0xea, 0x30, 0xb, 0x82, 0x23, 0x9f, + 0x40, 0xb7, 0x0, 0x0, 0x7e, 0xb, 0x70, 0x0, + 0x0, 0xf3, 0xb7, 0x0, 0x0, 0xe, 0x5b, 0x70, + 0x0, 0x0, 0xf3, 0xb7, 0x0, 0x0, 0x7e, 0xb, + 0x82, 0x23, 0x9f, 0x40, 0xbf, 0xff, 0xeb, 0x30, + 0x0, + + /* U+0045 "E" */ + 0xbf, 0xff, 0xff, 0x3b, 0x82, 0x22, 0x20, 0xb7, + 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xbf, 0xff, + 0xfa, 0xb, 0x82, 0x22, 0x10, 0xb7, 0x0, 0x0, + 0xb, 0x82, 0x22, 0x20, 0xbf, 0xff, 0xff, 0x50, + + /* U+0046 "F" */ + 0xbf, 0xff, 0xff, 0x3b, 0x82, 0x22, 0x20, 0xb7, + 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xbf, 0xff, + 0xfa, 0xb, 0x82, 0x22, 0x10, 0xb7, 0x0, 0x0, + 0xb, 0x70, 0x0, 0x0, 0xb7, 0x0, 0x0, 0x0, + + /* U+0047 "G" */ + 0x0, 0x3b, 0xef, 0xc4, 0x0, 0x5f, 0x94, 0x38, + 0xe1, 0xe, 0x70, 0x0, 0x0, 0x4, 0xe0, 0x0, + 0x0, 0x0, 0x6c, 0x0, 0x0, 0x8, 0x24, 0xe0, + 0x0, 0x0, 0xe3, 0xe, 0x60, 0x0, 0xe, 0x30, + 0x5f, 0x93, 0x37, 0xf3, 0x0, 0x3b, 0xef, 0xc4, + 0x0, + + /* U+0048 "H" */ + 0xb7, 0x0, 0x0, 0xb7, 0xb7, 0x0, 0x0, 0xb7, + 0xb7, 0x0, 0x0, 0xb7, 0xb7, 0x0, 0x0, 0xb7, + 0xbf, 0xff, 0xff, 0xf7, 0xb8, 0x22, 0x22, 0xc7, + 0xb7, 0x0, 0x0, 0xb7, 0xb7, 0x0, 0x0, 0xb7, + 0xb7, 0x0, 0x0, 0xb7, + + /* U+0049 "I" */ + 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, 0xb7, + 0xb7, + + /* U+004A "J" */ + 0x4, 0xff, 0xff, 0x0, 0x22, 0x5f, 0x0, 0x0, + 0x3f, 0x0, 0x0, 0x3f, 0x0, 0x0, 0x3f, 0x0, + 0x0, 0x3f, 0x0, 0x0, 0x4e, 0xd, 0x52, 0xba, + 0x5, 0xdf, 0xb2, + + /* U+004B "K" */ + 0xb7, 0x0, 0x7, 0xd1, 0xb7, 0x0, 0x5e, 0x20, + 0xb7, 0x4, 0xe3, 0x0, 0xb7, 0x3e, 0x40, 0x0, + 0xb9, 0xef, 0x20, 0x0, 0xbf, 0x89, 0xd0, 0x0, + 0xba, 0x0, 0xca, 0x0, 0xb7, 0x0, 0x1e, 0x70, + 0xb7, 0x0, 0x3, 0xf3, + + /* U+004C "L" */ + 0xb7, 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xb7, + 0x0, 0x0, 0xb, 0x70, 0x0, 0x0, 0xb7, 0x0, + 0x0, 0xb, 0x70, 0x0, 0x0, 0xb7, 0x0, 0x0, + 0xb, 0x82, 0x22, 0x20, 0xbf, 0xff, 0xff, 0x0, + + /* U+004D "M" */ + 0xb8, 0x0, 0x0, 0x1, 0xf2, 0xbf, 0x10, 0x0, + 0x9, 0xf3, 0xbe, 0xa0, 0x0, 0x2e, 0xf3, 0xb7, + 0xe3, 0x0, 0xb7, 0xf3, 0xb6, 0x7b, 0x4, 0xd0, + 0xf3, 0xb6, 0xd, 0x4c, 0x50, 0xf3, 0xb6, 0x5, + 0xfc, 0x0, 0xf3, 0xb6, 0x0, 0xb3, 0x0, 0xf3, + 0xb6, 0x0, 0x0, 0x0, 0xf3, + + /* U+004E "N" */ + 0xb9, 0x0, 0x0, 0xb7, 0xbf, 0x50, 0x0, 0xb7, + 0xbc, 0xf2, 0x0, 0xb7, 0xb7, 0xad, 0x0, 0xb7, + 0xb7, 0xd, 0x90, 0xb7, 0xb7, 0x2, 0xf5, 0xb7, + 0xb7, 0x0, 0x6f, 0xd7, 0xb7, 0x0, 0xa, 0xf7, + 0xb7, 0x0, 0x0, 0xd7, + + /* U+004F "O" */ + 0x0, 0x3b, 0xef, 0xb4, 0x0, 0x5, 0xf9, 0x33, + 0x8f, 0x60, 0xe, 0x60, 0x0, 0x5, 0xf1, 0x4e, + 0x0, 0x0, 0x0, 0xd5, 0x6c, 0x0, 0x0, 0x0, + 0xb7, 0x4e, 0x0, 0x0, 0x0, 0xd5, 0xe, 0x60, + 0x0, 0x5, 0xf1, 0x5, 0xf9, 0x33, 0x8f, 0x60, + 0x0, 0x3b, 0xef, 0xb4, 0x0, + + /* U+0050 "P" */ + 0xbf, 0xff, 0xd8, 0x0, 0xb8, 0x22, 0x5d, 0x90, + 0xb7, 0x0, 0x4, 0xe0, 0xb7, 0x0, 0x3, 0xf0, + 0xb7, 0x0, 0x2c, 0xa0, 0xbf, 0xff, 0xfa, 0x10, + 0xb8, 0x22, 0x0, 0x0, 0xb7, 0x0, 0x0, 0x0, + 0xb7, 0x0, 0x0, 0x0, + + /* U+0051 "Q" */ + 0x0, 0x3b, 0xef, 0xb4, 0x0, 0x4, 0xf9, 0x33, + 0x8f, 0x60, 0xe, 0x60, 0x0, 0x5, 0xf1, 0x4e, + 0x0, 0x0, 0x0, 0xd5, 0x6c, 0x0, 0x0, 0x0, + 0xb7, 0x4e, 0x0, 0x0, 0x0, 0xd6, 0xf, 0x60, + 0x0, 0x5, 0xf1, 0x5, 0xf8, 0x32, 0x7f, 0x60, + 0x0, 0x4c, 0xff, 0xc5, 0x0, 0x0, 0x0, 0xc, + 0xb0, 0x28, 0x0, 0x0, 0x1, 0xbf, 0xe5, 0x0, + 0x0, 0x0, 0x0, 0x0, + + /* U+0052 "R" */ + 0xbf, 0xff, 0xd8, 0x0, 0xb8, 0x22, 0x5d, 0x90, + 0xb7, 0x0, 0x4, 0xe0, 0xb7, 0x0, 0x3, 0xf0, + 0xb7, 0x0, 0x1b, 0xb0, 0xbf, 0xff, 0xfb, 0x10, + 0xb8, 0x22, 0xb9, 0x0, 0xb7, 0x0, 0x1f, 0x30, + 0xb7, 0x0, 0x7, 0xd0, + + /* U+0053 "S" */ + 0x3, 0xcf, 0xeb, 0x31, 0xf7, 0x23, 0x74, 0x4e, + 0x0, 0x0, 0x1, 0xf9, 0x20, 0x0, 0x2, 0xbf, + 0xd7, 0x0, 0x0, 0x4, 0xca, 0x0, 0x0, 0x4, + 0xe5, 0xb4, 0x23, 0xbb, 0x8, 0xdf, 0xea, 0x10, + + /* U+0054 "T" */ + 0xff, 0xff, 0xff, 0xf2, 0x23, 0xf3, 0x22, 0x0, + 0x1f, 0x10, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1f, + 0x10, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1f, 0x10, + 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1f, 0x10, 0x0, + + /* U+0055 "U" */ + 0xd6, 0x0, 0x0, 0xe4, 0xd6, 0x0, 0x0, 0xe4, + 0xd6, 0x0, 0x0, 0xe4, 0xd6, 0x0, 0x0, 0xe4, + 0xd6, 0x0, 0x0, 0xe4, 0xc7, 0x0, 0x0, 0xf3, + 0x9a, 0x0, 0x2, 0xf1, 0x2f, 0x83, 0x5d, 0xa0, + 0x4, 0xcf, 0xe8, 0x0, + + /* U+0056 "V" */ + 0xc, 0x70, 0x0, 0x0, 0xd5, 0x6, 0xe0, 0x0, + 0x4, 0xe0, 0x0, 0xf4, 0x0, 0xa, 0x80, 0x0, + 0x9b, 0x0, 0x1f, 0x20, 0x0, 0x2f, 0x20, 0x7b, + 0x0, 0x0, 0xc, 0x80, 0xe4, 0x0, 0x0, 0x5, + 0xe5, 0xe0, 0x0, 0x0, 0x0, 0xee, 0x70, 0x0, + 0x0, 0x0, 0x8f, 0x10, 0x0, + + /* U+0057 "W" */ + 0x7c, 0x0, 0x0, 0xe8, 0x0, 0x2, 0xf0, 0x2f, + 0x10, 0x3, 0xfd, 0x0, 0x7, 0xa0, 0xd, 0x60, + 0x8, 0x9f, 0x20, 0xc, 0x50, 0x8, 0xb0, 0xe, + 0x3b, 0x70, 0x1f, 0x0, 0x3, 0xf0, 0x3e, 0x6, + 0xc0, 0x6b, 0x0, 0x0, 0xe5, 0x89, 0x1, 0xf1, + 0xb6, 0x0, 0x0, 0x9a, 0xd4, 0x0, 0xb7, 0xf1, + 0x0, 0x0, 0x4f, 0xe0, 0x0, 0x6f, 0xc0, 0x0, + 0x0, 0xf, 0xa0, 0x0, 0x1f, 0x70, 0x0, + + /* U+0058 "X" */ + 0x5f, 0x10, 0x0, 0xe5, 0xa, 0xb0, 0x9, 0xa0, + 0x1, 0xe6, 0x4e, 0x10, 0x0, 0x4f, 0xe4, 0x0, + 0x0, 0xd, 0xe0, 0x0, 0x0, 0x7d, 0xd8, 0x0, + 0x2, 0xf3, 0x2f, 0x30, 0xc, 0x80, 0x7, 0xd0, + 0x8d, 0x0, 0x0, 0xc9, + + /* U+0059 "Y" */ + 0xc, 0x80, 0x0, 0xa, 0x80, 0x3f, 0x10, 0x3, + 0xe0, 0x0, 0xaa, 0x0, 0xc6, 0x0, 0x1, 0xf3, + 0x5d, 0x0, 0x0, 0x7, 0xce, 0x40, 0x0, 0x0, + 0xe, 0xb0, 0x0, 0x0, 0x0, 0xb7, 0x0, 0x0, + 0x0, 0xb, 0x70, 0x0, 0x0, 0x0, 0xb7, 0x0, + 0x0, + + /* U+005A "Z" */ + 0x6f, 0xff, 0xff, 0xf5, 0x2, 0x22, 0x29, 0xd0, + 0x0, 0x0, 0x3f, 0x30, 0x0, 0x1, 0xe6, 0x0, + 0x0, 0xb, 0xa0, 0x0, 0x0, 0x8d, 0x0, 0x0, + 0x4, 0xf2, 0x0, 0x0, 0x1e, 0x82, 0x22, 0x21, + 0x7f, 0xff, 0xff, 0xf8, + + /* U+0061 "a" */ + 0x8, 0xdf, 0xc3, 0x0, 0xa4, 0x29, 0xd0, 0x0, + 0x0, 0x1f, 0x10, 0x8d, 0xee, 0xf2, 0x4e, 0x10, + 0xf, 0x24, 0xe0, 0x7, 0xf2, 0x9, 0xed, 0x8f, + 0x20, + + /* U+0062 "b" */ + 0xe4, 0x0, 0x0, 0xe, 0x40, 0x0, 0x0, 0xe4, + 0x0, 0x0, 0xe, 0x7c, 0xfc, 0x40, 0xef, 0x52, + 0x7f, 0x2e, 0x60, 0x0, 0xb8, 0xe4, 0x0, 0x8, + 0xae, 0x60, 0x0, 0xb8, 0xef, 0x52, 0x8f, 0x2e, + 0x6d, 0xfc, 0x40, + + /* U+0063 "c" */ + 0x2, 0xbf, 0xe8, 0x0, 0xda, 0x24, 0xc3, 0x5d, + 0x0, 0x0, 0x7, 0xb0, 0x0, 0x0, 0x5d, 0x0, + 0x0, 0x0, 0xda, 0x24, 0xd3, 0x2, 0xbf, 0xe8, + 0x0, + + /* U+0064 "d" */ + 0x0, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1, 0xf1, + 0x0, 0x0, 0x1, 0xf1, 0x2, 0xbf, 0xd6, 0xf1, + 0xe, 0x92, 0x3d, 0xf1, 0x5d, 0x0, 0x4, 0xf1, + 0x7b, 0x0, 0x1, 0xf1, 0x5d, 0x0, 0x3, 0xf1, + 0xe, 0x91, 0x2d, 0xf1, 0x2, 0xbf, 0xe6, 0xf1, + + /* U+0065 "e" */ + 0x2, 0xbf, 0xd5, 0x0, 0xe8, 0x14, 0xe4, 0x5c, + 0x0, 0x6, 0xb7, 0xfe, 0xee, 0xec, 0x5d, 0x0, + 0x0, 0x0, 0xe9, 0x23, 0xa2, 0x2, 0xbf, 0xe9, + 0x0, + + /* U+0066 "f" */ + 0x1, 0xcf, 0x60, 0x9a, 0x11, 0xb, 0x60, 0xd, + 0xff, 0xf3, 0xb, 0x60, 0x0, 0xb6, 0x0, 0xb, + 0x60, 0x0, 0xb6, 0x0, 0xb, 0x60, 0x0, 0xb6, + 0x0, + + /* U+0067 "g" */ + 0x2, 0xbf, 0xe6, 0xe2, 0xe, 0xa2, 0x3c, 0xf2, + 0x5d, 0x0, 0x2, 0xf2, 0x7b, 0x0, 0x0, 0xf2, + 0x5d, 0x0, 0x2, 0xf2, 0xe, 0xa2, 0x3d, 0xf2, + 0x2, 0xbf, 0xe5, 0xf2, 0x0, 0x0, 0x2, 0xf0, + 0xc, 0x62, 0x3b, 0xa0, 0x6, 0xdf, 0xea, 0x10, + + /* U+0068 "h" */ + 0xe4, 0x0, 0x0, 0xe, 0x40, 0x0, 0x0, 0xe4, + 0x0, 0x0, 0xe, 0x7d, 0xfc, 0x20, 0xee, 0x42, + 0xac, 0xe, 0x60, 0x2, 0xf0, 0xe4, 0x0, 0xf, + 0x1e, 0x40, 0x0, 0xf2, 0xe4, 0x0, 0xf, 0x2e, + 0x40, 0x0, 0xf2, + + /* U+0069 "i" */ + 0xd, 0x40, 0x82, 0x0, 0x0, 0xe4, 0xe, 0x40, + 0xe4, 0xe, 0x40, 0xe4, 0xe, 0x40, 0xe4, + + /* U+006A "j" */ + 0x0, 0xd, 0x50, 0x0, 0x72, 0x0, 0x0, 0x0, + 0x0, 0xd4, 0x0, 0xd, 0x40, 0x0, 0xd4, 0x0, + 0xd, 0x40, 0x0, 0xd4, 0x0, 0xd, 0x40, 0x0, + 0xd4, 0x0, 0xd, 0x40, 0x22, 0xf2, 0xd, 0xf8, + 0x0, + + /* U+006B "k" */ + 0xe4, 0x0, 0x0, 0xe, 0x40, 0x0, 0x0, 0xe4, + 0x0, 0x0, 0xe, 0x40, 0xb, 0xa0, 0xe4, 0xb, + 0xb0, 0xe, 0x4b, 0xc0, 0x0, 0xee, 0xfd, 0x0, + 0xe, 0xc1, 0xd9, 0x0, 0xe4, 0x2, 0xf4, 0xe, + 0x40, 0x6, 0xe1, + + /* U+006C "l" */ + 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, 0xe4, + 0xe4, 0xe4, + + /* U+006D "m" */ + 0xe7, 0xdf, 0xb2, 0x9e, 0xe8, 0xe, 0xd3, 0x2c, + 0xfb, 0x23, 0xe5, 0xe6, 0x0, 0x4f, 0x10, 0x9, + 0x9e, 0x40, 0x3, 0xf0, 0x0, 0x8a, 0xe4, 0x0, + 0x3f, 0x0, 0x8, 0xae, 0x40, 0x3, 0xf0, 0x0, + 0x8a, 0xe4, 0x0, 0x3f, 0x0, 0x8, 0xa0, + + /* U+006E "n" */ + 0xe6, 0xdf, 0xc2, 0xe, 0xe4, 0x1a, 0xc0, 0xe6, + 0x0, 0x1f, 0xe, 0x40, 0x0, 0xf1, 0xe4, 0x0, + 0xf, 0x2e, 0x40, 0x0, 0xf2, 0xe4, 0x0, 0xf, + 0x20, + + /* U+006F "o" */ + 0x2, 0xbf, 0xe8, 0x0, 0xe, 0xa2, 0x3e, 0x80, + 0x5d, 0x0, 0x4, 0xf0, 0x7b, 0x0, 0x1, 0xf1, + 0x5d, 0x0, 0x4, 0xf0, 0xd, 0xa2, 0x3e, 0x80, + 0x2, 0xbf, 0xe8, 0x0, + + /* U+0070 "p" */ + 0xe7, 0xdf, 0xc4, 0xe, 0xf4, 0x16, 0xf2, 0xe6, + 0x0, 0xa, 0x8e, 0x40, 0x0, 0x8a, 0xe7, 0x0, + 0xb, 0x8e, 0xf5, 0x28, 0xf2, 0xe6, 0xcf, 0xc4, + 0xe, 0x40, 0x0, 0x0, 0xe4, 0x0, 0x0, 0xe, + 0x40, 0x0, 0x0, + + /* U+0071 "q" */ + 0x2, 0xbf, 0xd5, 0xf1, 0xe, 0xa2, 0x3e, 0xf1, + 0x5d, 0x0, 0x4, 0xf1, 0x7b, 0x0, 0x1, 0xf1, + 0x5d, 0x0, 0x4, 0xf1, 0xe, 0xa2, 0x3e, 0xf1, + 0x2, 0xbf, 0xd5, 0xf1, 0x0, 0x0, 0x1, 0xf1, + 0x0, 0x0, 0x1, 0xf1, 0x0, 0x0, 0x1, 0xf1, + + /* U+0072 "r" */ + 0xe6, 0xd8, 0xee, 0x61, 0xe7, 0x0, 0xe4, 0x0, + 0xe4, 0x0, 0xe4, 0x0, 0xe4, 0x0, + + /* U+0073 "s" */ + 0x9, 0xef, 0xc2, 0x6d, 0x22, 0x61, 0x7d, 0x20, + 0x0, 0x9, 0xfe, 0x91, 0x0, 0x2, 0xc9, 0x56, + 0x22, 0xb8, 0x4c, 0xfe, 0xa0, + + /* U+0074 "t" */ + 0x5, 0x30, 0x0, 0xb6, 0x0, 0xdf, 0xff, 0x30, + 0xb6, 0x0, 0xb, 0x60, 0x0, 0xb6, 0x0, 0xb, + 0x60, 0x0, 0xaa, 0x11, 0x2, 0xdf, 0x60, + + /* U+0075 "u" */ + 0xf3, 0x0, 0x2f, 0xf, 0x30, 0x2, 0xf0, 0xf3, + 0x0, 0x2f, 0xf, 0x30, 0x2, 0xf0, 0xe4, 0x0, + 0x4f, 0xa, 0xb2, 0x2c, 0xf0, 0x1b, 0xfe, 0x6f, + 0x0, + + /* U+0076 "v" */ + 0xd, 0x50, 0x0, 0x98, 0x6, 0xc0, 0x0, 0xf2, + 0x1, 0xf2, 0x6, 0xb0, 0x0, 0xa8, 0xc, 0x50, + 0x0, 0x3e, 0x3e, 0x0, 0x0, 0xd, 0xd8, 0x0, + 0x0, 0x6, 0xf2, 0x0, + + /* U+0077 "w" */ + 0xc5, 0x0, 0x3f, 0x10, 0x7, 0x86, 0xa0, 0x9, + 0xf6, 0x0, 0xd3, 0x1f, 0x0, 0xe7, 0xb0, 0x2d, + 0x0, 0xb5, 0x4c, 0xe, 0x18, 0x80, 0x6, 0xa9, + 0x60, 0xa6, 0xd3, 0x0, 0x1e, 0xe1, 0x4, 0xed, + 0x0, 0x0, 0xbb, 0x0, 0xe, 0x80, 0x0, + + /* U+0078 "x" */ + 0x5d, 0x0, 0x4e, 0x10, 0xa9, 0x1e, 0x40, 0x1, + 0xed, 0x90, 0x0, 0x8, 0xf1, 0x0, 0x2, 0xeb, + 0xa0, 0x0, 0xc7, 0xd, 0x60, 0x7c, 0x0, 0x3f, + 0x20, + + /* U+0079 "y" */ + 0xd, 0x50, 0x0, 0x98, 0x7, 0xb0, 0x0, 0xe2, + 0x1, 0xf2, 0x5, 0xc0, 0x0, 0xa7, 0xb, 0x50, + 0x0, 0x4d, 0x1e, 0x0, 0x0, 0xe, 0xb9, 0x0, + 0x0, 0x8, 0xf3, 0x0, 0x0, 0x5, 0xd0, 0x0, + 0x5, 0x2c, 0x60, 0x0, 0x1c, 0xf9, 0x0, 0x0, + + /* U+007A "z" */ + 0x7f, 0xff, 0xfb, 0x0, 0x2, 0xf3, 0x0, 0xc, + 0x70, 0x0, 0x9c, 0x0, 0x4, 0xe1, 0x0, 0x1e, + 0x50, 0x0, 0x8f, 0xff, 0xfd, + + /* U+00B0 "°" */ + 0x6, 0xb7, 0x3, 0x80, 0x84, 0x64, 0x3, 0x73, + 0x80, 0x84, 0x6, 0xb7, 0x0, + + /* U+00E8 "è" */ + 0x2, 0xd5, 0x0, 0x0, 0x1, 0xc3, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x2b, 0xfd, 0x50, 0xe, 0x81, + 0x4e, 0x45, 0xc0, 0x0, 0x6b, 0x7f, 0xee, 0xee, + 0xc5, 0xd0, 0x0, 0x0, 0xe, 0x92, 0x3a, 0x20, + 0x2b, 0xfe, 0x90, + + /* U+00E9 "é" */ + 0x0, 0x1, 0xe5, 0x0, 0x0, 0xb5, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x2b, 0xfd, 0x50, 0xe, 0x81, + 0x4e, 0x45, 0xc0, 0x0, 0x6b, 0x7f, 0xee, 0xee, + 0xc5, 0xd0, 0x0, 0x0, 0xe, 0x92, 0x3a, 0x20, + 0x2b, 0xfe, 0x90, + + /* U+00EA "ê" */ + 0x0, 0x4f, 0xa0, 0x0, 0x2c, 0x29, 0x60, 0x0, + 0x0, 0x0, 0x0, 0x2b, 0xfd, 0x50, 0xe, 0x81, + 0x4e, 0x45, 0xc0, 0x0, 0x6b, 0x7f, 0xee, 0xee, + 0xc5, 0xd0, 0x0, 0x0, 0xe, 0x92, 0x3a, 0x20, + 0x2b, 0xfe, 0x90, + + /* U+00FB "û" */ + 0x1, 0xdd, 0x10, 0x0, 0xa5, 0x4b, 0x0, 0x0, + 0x0, 0x0, 0xf, 0x30, 0x2, 0xf0, 0xf3, 0x0, + 0x2f, 0xf, 0x30, 0x2, 0xf0, 0xf3, 0x0, 0x2f, + 0xe, 0x40, 0x4, 0xf0, 0xab, 0x22, 0xcf, 0x1, + 0xbf, 0xe6, 0xf0 +}; + + +/*--------------------- + * GLYPH DESCRIPTION + *--------------------*/ + +static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { + {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, + {.bitmap_index = 0, .adv_w = 52, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 0, .adv_w = 40, .box_w = 2, .box_h = 4, .ofs_x = 0, .ofs_y = 5}, + {.bitmap_index = 4, .adv_w = 44, .box_w = 3, .box_h = 2, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 7, .adv_w = 128, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 43, .adv_w = 71, .box_w = 4, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 61, .adv_w = 110, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 93, .adv_w = 110, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 125, .adv_w = 128, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 161, .adv_w = 110, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 193, .adv_w = 118, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 229, .adv_w = 115, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 261, .adv_w = 124, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 297, .adv_w = 118, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 329, .adv_w = 141, .box_w = 10, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 374, .adv_w = 145, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 410, .adv_w = 139, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 451, .adv_w = 159, .box_w = 9, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 492, .adv_w = 129, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 524, .adv_w = 122, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 556, .adv_w = 148, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 597, .adv_w = 156, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 633, .adv_w = 60, .box_w = 2, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 642, .adv_w = 98, .box_w = 6, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 669, .adv_w = 138, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 705, .adv_w = 114, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 737, .adv_w = 183, .box_w = 10, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 782, .adv_w = 156, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 818, .adv_w = 161, .box_w = 10, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 863, .adv_w = 139, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 899, .adv_w = 161, .box_w = 10, .box_h = 12, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 959, .adv_w = 140, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 995, .adv_w = 119, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1027, .adv_w = 113, .box_w = 7, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1059, .adv_w = 152, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1095, .adv_w = 137, .box_w = 10, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 1140, .adv_w = 216, .box_w = 14, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1203, .adv_w = 129, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1239, .adv_w = 124, .box_w = 9, .box_h = 9, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 1280, .adv_w = 126, .box_w = 8, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1316, .adv_w = 115, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1341, .adv_w = 131, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1376, .adv_w = 110, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1401, .adv_w = 131, .box_w = 8, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1441, .adv_w = 118, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1466, .adv_w = 68, .box_w = 5, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1491, .adv_w = 132, .box_w = 8, .box_h = 10, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 1531, .adv_w = 131, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1566, .adv_w = 54, .box_w = 3, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1581, .adv_w = 55, .box_w = 5, .box_h = 13, .ofs_x = -2, .ofs_y = -3}, + {.bitmap_index = 1614, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1649, .adv_w = 54, .box_w = 2, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1659, .adv_w = 203, .box_w = 11, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1698, .adv_w = 131, .box_w = 7, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1723, .adv_w = 122, .box_w = 8, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1751, .adv_w = 131, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = -3}, + {.bitmap_index = 1786, .adv_w = 131, .box_w = 8, .box_h = 10, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 1826, .adv_w = 79, .box_w = 4, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1840, .adv_w = 96, .box_w = 6, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1861, .adv_w = 79, .box_w = 5, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1884, .adv_w = 130, .box_w = 7, .box_h = 7, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1909, .adv_w = 107, .box_w = 8, .box_h = 7, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 1937, .adv_w = 173, .box_w = 11, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1976, .adv_w = 106, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2001, .adv_w = 107, .box_w = 8, .box_h = 10, .ofs_x = -1, .ofs_y = -3}, + {.bitmap_index = 2041, .adv_w = 100, .box_w = 6, .box_h = 7, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2062, .adv_w = 80, .box_w = 5, .box_h = 5, .ofs_x = 0, .ofs_y = 5}, + {.bitmap_index = 2075, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2110, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2145, .adv_w = 118, .box_w = 7, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2180, .adv_w = 130, .box_w = 7, .box_h = 10, .ofs_x = 1, .ofs_y = 0} +}; + +/*--------------------- + * CHARACTER MAPPING + *--------------------*/ + +static const uint16_t unicode_list_0[] = { + 0x0, 0x7, 0xe +}; + +static const uint16_t unicode_list_4[] = { + 0x0, 0x38, 0x39, 0x3a, 0x4b +}; + +/*Collect the unicode lists and glyph_id offsets*/ +static const lv_font_fmt_txt_cmap_t cmaps[] = +{ + { + .range_start = 32, .range_length = 15, .glyph_id_start = 1, + .unicode_list = unicode_list_0, .glyph_id_ofs_list = NULL, .list_length = 3, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY + }, + { + .range_start = 48, .range_length = 10, .glyph_id_start = 4, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 65, .range_length = 26, .glyph_id_start = 14, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 97, .range_length = 26, .glyph_id_start = 40, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 176, .range_length = 76, .glyph_id_start = 66, + .unicode_list = unicode_list_4, .glyph_id_ofs_list = NULL, .list_length = 5, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY + } +}; + +/*----------------- + * KERNING + *----------------*/ + + +/*Map glyph_ids to kern left classes*/ +static const uint8_t kern_left_class_mapping[] = +{ + 0, 0, 1, 2, 3, 0, 4, 5, + 6, 7, 8, 9, 10, 3, 11, 12, + 13, 14, 15, 16, 17, 18, 18, 19, + 20, 21, 18, 18, 14, 22, 14, 23, + 24, 25, 19, 26, 26, 27, 28, 29, + 30, 31, 32, 33, 34, 35, 36, 30, + 36, 36, 37, 33, 30, 30, 31, 31, + 38, 39, 40, 41, 36, 42, 42, 43, + 42, 44, 45, 34, 34, 34, 36 +}; + +/*Map glyph_ids to kern right classes*/ +static const uint8_t kern_right_class_mapping[] = +{ + 0, 0, 1, 2, 3, 4, 5, 6, + 7, 8, 3, 9, 10, 11, 12, 13, + 14, 13, 13, 13, 14, 13, 13, 15, + 13, 13, 13, 13, 14, 13, 14, 13, + 16, 17, 18, 19, 19, 20, 21, 22, + 23, 24, 25, 25, 25, 0, 25, 24, + 26, 27, 24, 24, 28, 28, 25, 28, + 25, 28, 29, 30, 31, 32, 32, 33, + 32, 34, 35, 25, 25, 25, 31 +}; + +/*Kern values between classes*/ +static const int8_t kern_class_values[] = +{ + 9, -11, 1, 9, 4, 3, -8, 1, + 9, 1, 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 4, -11, 0, -2, -2, 2, + 2, -2, 0, -2, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, -12, 1, -2, + 0, -1, -1, -2, 0, 0, -1, 0, + 0, -2, 0, 0, -4, 0, -4, 0, + -5, -6, -6, -4, 0, 0, 0, 0, + -2, 0, 0, 2, 0, 1, -2, 0, + 1, 0, 2, -1, 0, 0, 0, -4, + 0, -1, 0, 0, 1, 0, 0, 2, + 0, -1, 0, -2, 0, -3, 0, 0, + 0, -2, 0, 0, 0, 0, 0, -1, + 1, -1, -1, 0, -2, 0, 0, 0, + -1, -1, 0, -2, -2, 0, 0, 1, + 0, 0, 0, 0, -1, 0, -2, -2, + -2, 0, 0, 0, 0, 0, -1, 0, + 0, 0, 0, -1, -2, 0, -3, -6, + 4, 0, -5, -1, -2, 0, -1, -9, + 2, -1, 0, 0, 2, 1, -1, -10, + 0, -10, -2, -17, -1, 5, 0, 2, + 0, 0, 0, 0, 0, 0, -3, -2, + 0, -6, 0, 0, 0, 0, -1, -1, + 0, -1, -2, 0, 0, 0, 0, 0, + -2, 0, -2, 0, -1, -2, -2, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -2, -2, 0, -2, -1, 2, 0, + 0, 0, 0, 0, 0, -1, 0, 0, + 1, 0, 0, 0, 0, -2, 0, -2, + -1, -2, 0, 0, 0, 2, 0, -2, + 0, 0, 0, 0, -2, -3, 0, -4, + 6, -10, -4, 2, 0, -2, -12, -3, + 0, -3, 0, -12, 0, -3, -5, -1, + 0, 0, 1, -1, 2, -1, -7, 0, + -10, -5, -4, -5, -6, -2, -5, 0, + -4, -5, 1, 1, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -1, 0, + 0, -1, 0, -2, 0, -3, -4, -4, + -1, 0, 0, 0, 0, -2, 0, 0, + 0, 0, 1, -1, 0, 0, -8, 6, + -2, -8, 0, 2, -3, 0, -10, -1, + -2, 2, 0, -2, 3, 0, -7, -3, + -7, -6, -8, 0, 0, 0, -1, 0, + 0, 0, -1, -1, -2, -5, -6, 0, + -18, 0, 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -2, 0, -1, -2, -3, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 2, -4, 2, + -1, -1, -5, -2, 0, -2, -2, -3, + 0, -3, 0, -1, -2, -1, -1, -3, + -2, 0, -1, 0, -4, 0, 0, 0, + -4, 0, -3, 0, -3, -3, 2, -3, + -4, 0, -2, -2, -2, 0, 0, 0, + 0, 0, -2, 0, 0, -3, 0, -2, + 0, -4, -5, -6, -2, 0, 0, 0, + 0, 15, 0, 0, 1, 0, 0, -2, + 0, 2, 0, 2, -3, 0, -1, -2, + -6, -1, -1, -1, -1, 0, 0, -1, + 0, 0, 0, 0, -2, -2, -2, 0, + -1, 0, -1, 0, 0, 0, -1, -2, + -1, -2, -2, -2, 0, 8, -2, -2, + 3, 0, 0, -9, -3, 2, -3, 1, + -6, 0, -2, -3, -1, 1, 0, 0, + -3, 0, 0, -4, 0, -3, -2, -3, + -2, -2, 0, -3, 1, -4, -3, 6, + 0, 2, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, -1, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, -2, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -3, 0, 0, 0, 0, -2, 0, + 0, -2, -2, 0, 0, 0, 0, 0, + -1, 0, 0, 0, 0, 0, -1, 0, + 0, 0, 0, -4, 4, 0, -1, -9, + 0, 0, -4, -2, -5, 0, -5, 0, + -3, -8, -2, -8, -7, -9, 0, -2, + 0, -4, -2, -1, -2, -3, -5, -3, + -7, -8, -4, -2, 0, 6, -4, -7, + 0, 1, -6, 0, -10, -1, -2, 1, + 0, -2, 0, -1, -12, -2, -10, -2, + -14, 0, 1, 0, -1, 0, 0, 0, + 0, -1, -1, -7, -1, 0, -12, 0, + -5, 0, 0, -1, -3, -6, -2, 0, + -1, 0, -9, -2, 0, -6, 0, -6, + -2, -3, -5, -2, -3, -3, 0, -2, + -4, -2, -4, 0, 1, 0, -1, -6, + 0, 4, 0, 0, 0, 0, 0, -1, + -4, 0, 0, 0, 0, 0, 0, 0, + -2, 0, -2, 0, 0, -4, -2, 0, + -1, 0, 0, 0, 0, 0, 0, 1, + 0, 0, 0, 0, 3, -6, 4, 0, + -2, 0, -1, 2, 0, -2, 0, -2, + 0, 0, 0, 0, 0, -2, 0, 0, + -2, -3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -2, -2, 0, -3, + 2, -6, -4, 8, 3, 2, -17, -1, + 4, -2, 0, -7, 0, -2, -2, -2, + 2, -2, -2, -6, -2, 0, -5, 0, + -11, -2, 6, -2, -7, 1, -2, -6, + -6, -2, 8, 0, -7, -5, 6, 0, + 1, -14, -2, 2, -3, -1, -7, -3, + -4, -3, -3, -2, 0, 0, -4, -4, + -2, -11, 0, -11, -3, 0, -7, -11, + -1, -6, -3, -6, -5, 5, 0, 0, + -6, 2, 0, 0, -10, 0, -2, -4, + -3, -6, -4, -5, 0, -2, -6, -2, + -4, -4, -6, -2, -3, 0, -6, -2, + 0, -2, -4, -4, -5, -5, -7, -2, + -4, 0, -7, -6, 6, -2, 1, -18, + -3, 4, -4, -3, -8, -2, -6, -2, + -3, -2, -2, -4, -6, -1, 0, -12, + 0, -12, -4, 5, -7, -13, -4, -7, + -8, -10, -6, 4, 0, 4, -4, 4, + 0, 0, -6, -1, 0, -1, 0, 0, + 0, -2, 0, 0, 0, 0, 0, -2, + 0, 0, 0, 0, -2, 0, 0, 0, + 0, -1, -1, -2, 0, 0, 0, 0, + 0, 0, -4, -1, 0, 0, 0, -4, + 0, -2, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 1, + 0, 0, 0, 0, 0, 0, -2, 0, + 0, -4, -3, -2, 0, -5, -2, -4, + 0, 0, -5, 0, -2, -2, 0, 0, + 0, 0, -16, -4, -8, -2, -7, 0, + -1, 0, 0, 0, 0, 0, 0, 0, + 0, -3, -3, -2, -3, 0, 4, -1, + -4, -1, -3, -4, 0, -2, -1, -1, + 0, 0, -1, 0, 0, -17, -2, -3, + 0, -4, 0, 0, -1, -2, 0, 0, + 0, 0, 1, 0, -1, -3, -1, 3, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 2, 0, 0, + 0, 0, 0, -4, 0, 0, -5, -2, + -4, 0, 0, -5, 0, -2, 0, 0, + 0, 0, 0, -19, 0, -4, -7, -10, + 0, -3, 0, 0, 0, 0, 0, 0, + 0, 0, -2, -3, -1, -3, 0, -2, + 2, 9, 3, 4, -5, 2, 8, 2, + 6, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -2, 0, -2, 15, + 8, 15, 0, 0, 0, 2, 0, 0, + 7, 0, 0, 0, -1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -3, -16, -2, -2, -8, -9, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 2, -2, 2, + 3, 2, -6, 0, 0, -2, 2, 0, + 0, 0, 0, 0, -5, 0, -2, -1, + -4, 0, -2, 0, -4, -1, 0, -1, + -3, 0, -2, -5, -4, -2, 0, 0, + 0, 0, -1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -3, -16, + -2, -2, -8, -9, 0, 0, 0, 0, + 0, 10, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -2, 1, -1, 1, -1, + -5, 0, 4, 0, 2, -8, -2, -5, + 0, -3, -7, -4, -5, -8, -7, 0, + -2, -1, -2, -1, 0, -1, -1, 3, + 0, 3, -1, 0, 6, 0, 0, 0, + -1, -2, -2, 0, 0, -5, 0, -1, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -2, -2, 0, -2, + 0, 2, -3, -4, -1, 0, -6, -1, + -4, -1, -2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -3, 0, 0, 0, 0, -2, 0, -2, + 0, 0, -1, 0, -6, 1, 2, 2, + 0, -5, 1, 3, 1, 6, -5, 0, + -1, 0, -1, -8, 0, 0, -6, -5, + 0, -3, 0, -3, 0, -3, 0, -1, + 3, 0, -2, -6, -2, 7, 0, 0, + -2, 2, 0, 0, -6, 0, -1, -1, + 0, 0, 0, -2, 0, -2, -8, -2, + -4, 0, -6, 0, -2, 0, -3, 0, + 1, 0, -2, 0, -2, -6, 0, -2, + 2, 0, 1, 0, -2, -1, 0, -2, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -2, 0, 0, 0, 0, 0, 0, + -2, -2, 0, 0, 4, -12, 1, 8, + 6, 3, -8, 1, 8, 0, 7, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0 +}; + + +/*Collect the kern class' data in one place*/ +static const lv_font_fmt_txt_kern_classes_t kern_classes = +{ + .class_pair_values = kern_class_values, + .left_class_mapping = kern_left_class_mapping, + .right_class_mapping = kern_right_class_mapping, + .left_class_cnt = 45, + .right_class_cnt = 35, +}; + +/*-------------------- + * ALL CUSTOM DATA + *--------------------*/ + +#if LVGL_VERSION_MAJOR == 8 +/*Store all the custom data of the font*/ +static lv_font_fmt_txt_glyph_cache_t cache; +#endif + +#if LVGL_VERSION_MAJOR >= 8 +static const lv_font_fmt_txt_dsc_t font_dsc = { +#else +static lv_font_fmt_txt_dsc_t font_dsc = { +#endif + .glyph_bitmap = glyph_bitmap, + .glyph_dsc = glyph_dsc, + .cmaps = cmaps, + .kern_dsc = &kern_classes, + .kern_scale = 16, + .cmap_num = 5, + .bpp = 4, + .kern_classes = 1, + .bitmap_format = 0, +#if LVGL_VERSION_MAJOR == 8 + .cache = &cache +#endif +}; + + + +/*----------------- + * PUBLIC FONT + *----------------*/ + +/*Initialize a public general font descriptor*/ +#if LVGL_VERSION_MAJOR >= 8 +const lv_font_t montserrat_medium_12 = { +#else +lv_font_t montserrat_medium_12 = { +#endif + .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ + .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ + .line_height = 13, /*The maximum line height required by the font*/ + .base_line = 3, /*Baseline measured from the bottom of the line*/ +#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) + .subpx = LV_FONT_SUBPX_NONE, +#endif +#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 + .underline_position = -1, + .underline_thickness = 1, +#endif + .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ +#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 + .fallback = NULL, +#endif + .user_data = NULL, +}; + + + +#endif /*#if MONTSERRAT_MEDIUM_12*/ + diff --git a/main/fonts/montserrat_medium_18.c b/main/fonts/montserrat_medium_18.c index f00357b..70980b3 100644 --- a/main/fonts/montserrat_medium_18.c +++ b/main/fonts/montserrat_medium_18.c @@ -1,1198 +1,1259 @@ -/******************************************************************************* - * Size: 18 px - * Bpp: 4 - * Opts: --bpp 4 --size 18 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°éûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz ' --format lvgl -o montserrat_medium_18.c --font fa-solid-900.ttf --range 61461 - ******************************************************************************/ - -#ifdef LV_LVGL_H_INCLUDE_SIMPLE -#include "lvgl.h" -#else -#include "lvgl/lvgl.h" -#endif - -#ifndef MONTSERRAT_MEDIUM_18 -#define MONTSERRAT_MEDIUM_18 1 -#endif - -#if MONTSERRAT_MEDIUM_18 - -/*----------------- - * BITMAPS - *----------------*/ - -/*Store the image of the glyphs*/ -static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { - /* U+0020 " " */ - - /* U+0027 "'" */ - 0xda, 0xd9, 0xd9, 0xc8, 0xc8, 0x0, - - /* U+002E "." */ - 0x5, 0x60, 0x1f, 0xf2, 0xc, 0xd0, - - /* U+0030 "0" */ - 0x0, 0x4, 0xbe, 0xeb, 0x40, 0x0, 0x0, 0x6f, - 0xfb, 0xbf, 0xf6, 0x0, 0x2, 0xfd, 0x10, 0x1, - 0xdf, 0x20, 0xa, 0xf3, 0x0, 0x0, 0x3f, 0x90, - 0xe, 0xe0, 0x0, 0x0, 0xe, 0xe0, 0xf, 0xb0, - 0x0, 0x0, 0xb, 0xf0, 0x1f, 0xa0, 0x0, 0x0, - 0xa, 0xf1, 0xf, 0xb0, 0x0, 0x0, 0xb, 0xf0, - 0xe, 0xe0, 0x0, 0x0, 0xe, 0xe0, 0x9, 0xf3, - 0x0, 0x0, 0x3f, 0x90, 0x2, 0xfd, 0x10, 0x1, - 0xdf, 0x20, 0x0, 0x6f, 0xfb, 0xbf, 0xf6, 0x0, - 0x0, 0x4, 0xbe, 0xeb, 0x40, 0x0, - - /* U+0031 "1" */ - 0xdf, 0xff, 0xc8, 0xaa, 0xfc, 0x0, 0xf, 0xc0, - 0x0, 0xfc, 0x0, 0xf, 0xc0, 0x0, 0xfc, 0x0, - 0xf, 0xc0, 0x0, 0xfc, 0x0, 0xf, 0xc0, 0x0, - 0xfc, 0x0, 0xf, 0xc0, 0x0, 0xfc, 0x0, 0xf, - 0xc0, - - /* U+0032 "2" */ - 0x1, 0x8d, 0xfe, 0xc5, 0x0, 0x4f, 0xfd, 0xac, - 0xff, 0x70, 0x3c, 0x30, 0x0, 0x2f, 0xf0, 0x0, - 0x0, 0x0, 0xb, 0xf2, 0x0, 0x0, 0x0, 0xc, - 0xf1, 0x0, 0x0, 0x0, 0x3f, 0xb0, 0x0, 0x0, - 0x2, 0xee, 0x20, 0x0, 0x0, 0x2e, 0xf3, 0x0, - 0x0, 0x2, 0xef, 0x30, 0x0, 0x0, 0x2e, 0xf3, - 0x0, 0x0, 0x2, 0xef, 0x30, 0x0, 0x0, 0x2e, - 0xfc, 0xaa, 0xaa, 0xa7, 0x5f, 0xff, 0xff, 0xff, - 0xfb, - - /* U+0033 "3" */ - 0x5f, 0xff, 0xff, 0xff, 0xf0, 0x3a, 0xaa, 0xaa, - 0xcf, 0xc0, 0x0, 0x0, 0x1, 0xee, 0x10, 0x0, - 0x0, 0xc, 0xf3, 0x0, 0x0, 0x0, 0x9f, 0x60, - 0x0, 0x0, 0x4, 0xfe, 0x61, 0x0, 0x0, 0x5, - 0xdf, 0xff, 0x50, 0x0, 0x0, 0x0, 0x3e, 0xf2, - 0x0, 0x0, 0x0, 0x7, 0xf6, 0x0, 0x0, 0x0, - 0x6, 0xf6, 0x69, 0x10, 0x0, 0x1d, 0xf2, 0x9f, - 0xfc, 0xbc, 0xff, 0x80, 0x4, 0xae, 0xfe, 0xb5, - 0x0, - - /* U+0034 "4" */ - 0x0, 0x0, 0x0, 0x4f, 0xa0, 0x0, 0x0, 0x0, - 0x1, 0xed, 0x0, 0x0, 0x0, 0x0, 0xc, 0xf2, - 0x0, 0x0, 0x0, 0x0, 0x9f, 0x50, 0x0, 0x0, - 0x0, 0x5, 0xf9, 0x0, 0x0, 0x0, 0x0, 0x2f, - 0xc0, 0x3, 0xc5, 0x0, 0x0, 0xde, 0x10, 0x4, - 0xf7, 0x0, 0xb, 0xf4, 0x0, 0x4, 0xf7, 0x0, - 0x4f, 0xff, 0xff, 0xff, 0xff, 0xfd, 0x39, 0x99, - 0x99, 0x9b, 0xfc, 0x98, 0x0, 0x0, 0x0, 0x5, - 0xf7, 0x0, 0x0, 0x0, 0x0, 0x5, 0xf7, 0x0, - 0x0, 0x0, 0x0, 0x5, 0xf7, 0x0, - - /* U+0035 "5" */ - 0x2, 0xff, 0xff, 0xff, 0xf0, 0x4, 0xfc, 0xaa, - 0xaa, 0xa0, 0x5, 0xf5, 0x0, 0x0, 0x0, 0x7, - 0xf3, 0x0, 0x0, 0x0, 0x9, 0xf1, 0x0, 0x0, - 0x0, 0xa, 0xff, 0xff, 0xc7, 0x0, 0x7, 0xaa, - 0xab, 0xff, 0xc0, 0x0, 0x0, 0x0, 0xb, 0xf6, - 0x0, 0x0, 0x0, 0x3, 0xfa, 0x0, 0x0, 0x0, - 0x3, 0xfa, 0x2c, 0x20, 0x0, 0xb, 0xf6, 0x6f, - 0xfd, 0xbb, 0xef, 0xb0, 0x3, 0x9d, 0xff, 0xc7, - 0x0, - - /* U+0036 "6" */ - 0x0, 0x1, 0x8d, 0xfe, 0xc6, 0x0, 0x4, 0xef, - 0xca, 0xad, 0x90, 0x1, 0xee, 0x40, 0x0, 0x0, - 0x0, 0x8f, 0x40, 0x0, 0x0, 0x0, 0xe, 0xe0, - 0x0, 0x0, 0x0, 0x0, 0xfb, 0x2a, 0xef, 0xd7, - 0x0, 0x1f, 0xdf, 0xd9, 0x9d, 0xfb, 0x1, 0xff, - 0xa0, 0x0, 0xa, 0xf5, 0xf, 0xf2, 0x0, 0x0, - 0x3f, 0x90, 0xbf, 0x20, 0x0, 0x3, 0xf8, 0x4, - 0xfa, 0x0, 0x0, 0xaf, 0x40, 0x9, 0xfd, 0x99, - 0xdf, 0xa0, 0x0, 0x5, 0xcf, 0xfc, 0x60, 0x0, - - /* U+0037 "7" */ - 0x7f, 0xff, 0xff, 0xff, 0xff, 0x7, 0xfb, 0xaa, - 0xaa, 0xaf, 0xe0, 0x7f, 0x40, 0x0, 0x5, 0xf8, - 0x6, 0xf4, 0x0, 0x0, 0xcf, 0x10, 0x0, 0x0, - 0x0, 0x3f, 0xa0, 0x0, 0x0, 0x0, 0xa, 0xf3, - 0x0, 0x0, 0x0, 0x1, 0xfc, 0x0, 0x0, 0x0, - 0x0, 0x8f, 0x50, 0x0, 0x0, 0x0, 0xe, 0xe0, - 0x0, 0x0, 0x0, 0x6, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0xdf, 0x10, 0x0, 0x0, 0x0, 0x4f, 0x90, - 0x0, 0x0, 0x0, 0xb, 0xf2, 0x0, 0x0, 0x0, - - /* U+0038 "8" */ - 0x0, 0x2a, 0xef, 0xfc, 0x70, 0x0, 0x3f, 0xfb, - 0x89, 0xdf, 0xb0, 0xa, 0xf5, 0x0, 0x0, 0xbf, - 0x30, 0xbf, 0x10, 0x0, 0x8, 0xf4, 0x4, 0xfc, - 0x42, 0x26, 0xfd, 0x0, 0x6, 0xff, 0xff, 0xfe, - 0x10, 0x5, 0xfe, 0x85, 0x6a, 0xfd, 0x10, 0xee, - 0x10, 0x0, 0x7, 0xf8, 0x2f, 0xa0, 0x0, 0x0, - 0x1f, 0xb2, 0xfb, 0x0, 0x0, 0x2, 0xfb, 0xd, - 0xf4, 0x0, 0x0, 0xaf, 0x70, 0x3f, 0xfb, 0x89, - 0xdf, 0xc0, 0x0, 0x29, 0xdf, 0xfc, 0x60, 0x0, - - /* U+0039 "9" */ - 0x0, 0x6c, 0xff, 0xc6, 0x0, 0x0, 0xaf, 0xd9, - 0x8c, 0xfa, 0x0, 0x3f, 0xb0, 0x0, 0x7, 0xf6, - 0x7, 0xf5, 0x0, 0x0, 0xf, 0xd0, 0x6f, 0x60, - 0x0, 0x2, 0xff, 0x11, 0xff, 0x51, 0x4, 0xdf, - 0xf2, 0x4, 0xef, 0xff, 0xfb, 0x9f, 0x30, 0x0, - 0x57, 0x73, 0xa, 0xf1, 0x0, 0x0, 0x0, 0x0, - 0xdf, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xa0, 0x0, - 0x0, 0x0, 0x3e, 0xf2, 0x0, 0x8e, 0xba, 0xcf, - 0xf5, 0x0, 0x5, 0xbe, 0xfd, 0x92, 0x0, 0x0, - - /* U+0041 "A" */ - 0x0, 0x0, 0x0, 0x8f, 0xa0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xe, 0xff, 0x20, 0x0, 0x0, 0x0, - 0x0, 0x6, 0xf6, 0xf9, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xdd, 0xb, 0xf0, 0x0, 0x0, 0x0, 0x0, - 0x4f, 0x60, 0x4f, 0x70, 0x0, 0x0, 0x0, 0xb, - 0xe0, 0x0, 0xdd, 0x0, 0x0, 0x0, 0x2, 0xf8, - 0x0, 0x6, 0xf5, 0x0, 0x0, 0x0, 0x9f, 0x10, - 0x0, 0xe, 0xc0, 0x0, 0x0, 0x1f, 0xff, 0xff, - 0xff, 0xff, 0x30, 0x0, 0x7, 0xf8, 0x88, 0x88, - 0x88, 0xfa, 0x0, 0x0, 0xed, 0x0, 0x0, 0x0, - 0xb, 0xf1, 0x0, 0x5f, 0x60, 0x0, 0x0, 0x0, - 0x4f, 0x80, 0xc, 0xf1, 0x0, 0x0, 0x0, 0x0, - 0xee, 0x0, - - /* U+0042 "B" */ - 0x1f, 0xff, 0xff, 0xfe, 0xb4, 0x0, 0x1f, 0xd8, - 0x88, 0x8a, 0xff, 0x70, 0x1f, 0xb0, 0x0, 0x0, - 0x2f, 0xf0, 0x1f, 0xb0, 0x0, 0x0, 0xc, 0xf0, - 0x1f, 0xb0, 0x0, 0x0, 0x2f, 0xc0, 0x1f, 0xd8, - 0x88, 0x8a, 0xfe, 0x30, 0x1f, 0xff, 0xff, 0xff, - 0xfd, 0x40, 0x1f, 0xb0, 0x0, 0x1, 0x4d, 0xf3, - 0x1f, 0xb0, 0x0, 0x0, 0x4, 0xf9, 0x1f, 0xb0, - 0x0, 0x0, 0x2, 0xfb, 0x1f, 0xb0, 0x0, 0x0, - 0x8, 0xf8, 0x1f, 0xd8, 0x88, 0x89, 0xcf, 0xe1, - 0x1f, 0xff, 0xff, 0xff, 0xd9, 0x10, - - /* U+0043 "C" */ - 0x0, 0x0, 0x4a, 0xef, 0xeb, 0x50, 0x0, 0x1, - 0xbf, 0xfc, 0xac, 0xff, 0xb0, 0x0, 0xbf, 0xb2, - 0x0, 0x1, 0x9c, 0x0, 0x6f, 0xb0, 0x0, 0x0, - 0x0, 0x0, 0xd, 0xf1, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, - 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xfc, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xd, 0xf1, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6f, 0xb0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xbf, 0xb2, 0x0, 0x1, 0xac, 0x10, - 0x1, 0xbf, 0xfc, 0xbc, 0xff, 0xb0, 0x0, 0x0, - 0x4b, 0xef, 0xeb, 0x50, 0x0, - - /* U+0044 "D" */ - 0x1f, 0xff, 0xff, 0xfd, 0xa4, 0x0, 0x1, 0xfe, - 0xaa, 0xaa, 0xcf, 0xfa, 0x0, 0x1f, 0xb0, 0x0, - 0x0, 0x2b, 0xfa, 0x1, 0xfb, 0x0, 0x0, 0x0, - 0xc, 0xf4, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x3f, - 0xb1, 0xfb, 0x0, 0x0, 0x0, 0x0, 0xee, 0x1f, - 0xb0, 0x0, 0x0, 0x0, 0xd, 0xf1, 0xfb, 0x0, - 0x0, 0x0, 0x0, 0xee, 0x1f, 0xb0, 0x0, 0x0, - 0x0, 0x3f, 0xb1, 0xfb, 0x0, 0x0, 0x0, 0xc, - 0xf4, 0x1f, 0xb0, 0x0, 0x0, 0x2b, 0xfa, 0x1, - 0xfe, 0xaa, 0xaa, 0xcf, 0xfa, 0x0, 0x1f, 0xff, - 0xff, 0xfd, 0xa4, 0x0, 0x0, - - /* U+0045 "E" */ - 0x1f, 0xff, 0xff, 0xff, 0xfc, 0x1, 0xfe, 0xaa, - 0xaa, 0xaa, 0x70, 0x1f, 0xb0, 0x0, 0x0, 0x0, - 0x1, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, - 0x0, 0x0, 0x0, 0x1, 0xfd, 0x99, 0x99, 0x99, - 0x0, 0x1f, 0xff, 0xff, 0xff, 0xf0, 0x1, 0xfb, - 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, - 0x0, 0x1, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x1f, - 0xb0, 0x0, 0x0, 0x0, 0x1, 0xfe, 0xaa, 0xaa, - 0xaa, 0xa0, 0x1f, 0xff, 0xff, 0xff, 0xff, 0x0, - - /* U+0046 "F" */ - 0x1f, 0xff, 0xff, 0xff, 0xfc, 0x1f, 0xea, 0xaa, - 0xaa, 0xa7, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, - 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, - 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xff, - 0xff, 0xff, 0xf0, 0x1f, 0xe9, 0x99, 0x99, 0x90, - 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, - 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, - 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, - 0x0, - - /* U+0047 "G" */ - 0x0, 0x0, 0x4a, 0xdf, 0xeb, 0x60, 0x0, 0x1, - 0xbf, 0xfc, 0xbb, 0xff, 0xc1, 0x0, 0xbf, 0xb2, - 0x0, 0x0, 0x7d, 0x10, 0x6f, 0xb0, 0x0, 0x0, - 0x0, 0x0, 0xd, 0xf1, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, - 0xa0, 0x0, 0x0, 0x0, 0x39, 0x30, 0xfc, 0x0, - 0x0, 0x0, 0x6, 0xf5, 0xc, 0xf1, 0x0, 0x0, - 0x0, 0x6f, 0x50, 0x6f, 0xb0, 0x0, 0x0, 0x6, - 0xf5, 0x0, 0xbf, 0xb2, 0x0, 0x0, 0x9f, 0x50, - 0x0, 0xaf, 0xfd, 0xbc, 0xff, 0xd2, 0x0, 0x0, - 0x4a, 0xef, 0xeb, 0x60, 0x0, - - /* U+0048 "H" */ - 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, - 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, - 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, - 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xea, - 0xaa, 0xaa, 0xaa, 0xfb, 0x1f, 0xff, 0xff, 0xff, - 0xff, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, - 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, - 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, - 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, - 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, - - /* U+0049 "I" */ - 0x1f, 0xb1, 0xfb, 0x1f, 0xb1, 0xfb, 0x1f, 0xb1, - 0xfb, 0x1f, 0xb1, 0xfb, 0x1f, 0xb1, 0xfb, 0x1f, - 0xb1, 0xfb, 0x1f, 0xb0, - - /* U+004A "J" */ - 0x0, 0xef, 0xff, 0xff, 0x70, 0x8, 0xaa, 0xab, - 0xf7, 0x0, 0x0, 0x0, 0x5f, 0x70, 0x0, 0x0, - 0x5, 0xf7, 0x0, 0x0, 0x0, 0x5f, 0x70, 0x0, - 0x0, 0x5, 0xf7, 0x0, 0x0, 0x0, 0x5f, 0x70, - 0x0, 0x0, 0x5, 0xf7, 0x0, 0x0, 0x0, 0x5f, - 0x70, 0x0, 0x0, 0x6, 0xf6, 0xa, 0x70, 0x0, - 0xcf, 0x30, 0xcf, 0xda, 0xdf, 0xc0, 0x0, 0x8d, - 0xfe, 0x90, 0x0, - - /* U+004B "K" */ - 0x1f, 0xb0, 0x0, 0x0, 0x1d, 0xe2, 0x1f, 0xb0, - 0x0, 0x1, 0xdf, 0x30, 0x1f, 0xb0, 0x0, 0xc, - 0xf4, 0x0, 0x1f, 0xb0, 0x0, 0xbf, 0x50, 0x0, - 0x1f, 0xb0, 0xb, 0xf7, 0x0, 0x0, 0x1f, 0xb0, - 0xaf, 0x80, 0x0, 0x0, 0x1f, 0xb9, 0xff, 0xb0, - 0x0, 0x0, 0x1f, 0xff, 0xbb, 0xf8, 0x0, 0x0, - 0x1f, 0xfb, 0x1, 0xdf, 0x50, 0x0, 0x1f, 0xd0, - 0x0, 0x2f, 0xf2, 0x0, 0x1f, 0xb0, 0x0, 0x4, - 0xfd, 0x10, 0x1f, 0xb0, 0x0, 0x0, 0x7f, 0xb0, - 0x1f, 0xb0, 0x0, 0x0, 0x9, 0xf8, - - /* U+004C "L" */ - 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, - 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, - 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, - 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, - 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, - 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, - 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, - 0xea, 0xaa, 0xaa, 0xa5, 0x1f, 0xff, 0xff, 0xff, - 0xf8, - - /* U+004D "M" */ - 0x1f, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0x41, - 0xff, 0x30, 0x0, 0x0, 0x0, 0x1f, 0xf4, 0x1f, - 0xfc, 0x0, 0x0, 0x0, 0x9, 0xff, 0x41, 0xff, - 0xf5, 0x0, 0x0, 0x2, 0xfe, 0xf4, 0x1f, 0xad, - 0xe0, 0x0, 0x0, 0xbe, 0x8f, 0x41, 0xfa, 0x4f, - 0x80, 0x0, 0x4f, 0x67, 0xf4, 0x1f, 0xa0, 0xaf, - 0x20, 0xd, 0xd0, 0x7f, 0x41, 0xfa, 0x2, 0xfa, - 0x7, 0xf4, 0x7, 0xf4, 0x1f, 0xa0, 0x8, 0xf5, - 0xea, 0x0, 0x7f, 0x41, 0xfa, 0x0, 0xe, 0xff, - 0x20, 0x6, 0xf4, 0x1f, 0xa0, 0x0, 0x5f, 0x80, - 0x0, 0x6f, 0x41, 0xfa, 0x0, 0x0, 0x60, 0x0, - 0x6, 0xf4, 0x1f, 0xa0, 0x0, 0x0, 0x0, 0x0, - 0x6f, 0x40, - - /* U+004E "N" */ - 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xf8, - 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xff, 0x50, 0x0, - 0x1, 0xfb, 0x1f, 0xdf, 0xf2, 0x0, 0x1, 0xfb, - 0x1f, 0xb6, 0xfd, 0x0, 0x1, 0xfb, 0x1f, 0xb0, - 0x9f, 0xa0, 0x1, 0xfb, 0x1f, 0xb0, 0xc, 0xf6, - 0x1, 0xfb, 0x1f, 0xb0, 0x1, 0xef, 0x31, 0xfb, - 0x1f, 0xb0, 0x0, 0x4f, 0xe2, 0xfb, 0x1f, 0xb0, - 0x0, 0x7, 0xfd, 0xfb, 0x1f, 0xb0, 0x0, 0x0, - 0xbf, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1d, 0xfb, - 0x1f, 0xb0, 0x0, 0x0, 0x2, 0xfb, - - /* U+004F "O" */ - 0x0, 0x0, 0x4a, 0xdf, 0xeb, 0x50, 0x0, 0x0, - 0x0, 0xaf, 0xfc, 0xbc, 0xff, 0xc1, 0x0, 0x0, - 0xbf, 0xb2, 0x0, 0x1, 0xaf, 0xd0, 0x0, 0x6f, - 0xb0, 0x0, 0x0, 0x0, 0x9f, 0x80, 0xc, 0xf1, - 0x0, 0x0, 0x0, 0x0, 0xfe, 0x0, 0xfc, 0x0, - 0x0, 0x0, 0x0, 0xa, 0xf2, 0x1f, 0xa0, 0x0, - 0x0, 0x0, 0x0, 0x9f, 0x30, 0xfc, 0x0, 0x0, - 0x0, 0x0, 0xa, 0xf2, 0xc, 0xf1, 0x0, 0x0, - 0x0, 0x0, 0xfe, 0x0, 0x6f, 0xb0, 0x0, 0x0, - 0x0, 0x9f, 0x80, 0x0, 0xbf, 0xb2, 0x0, 0x1, - 0xaf, 0xd0, 0x0, 0x0, 0xaf, 0xfc, 0xbc, 0xff, - 0xc1, 0x0, 0x0, 0x0, 0x4a, 0xef, 0xeb, 0x50, - 0x0, 0x0, - - /* U+0050 "P" */ - 0x1f, 0xff, 0xff, 0xfc, 0x70, 0x0, 0x1f, 0xea, - 0xaa, 0xbe, 0xfd, 0x10, 0x1f, 0xb0, 0x0, 0x0, - 0x9f, 0x90, 0x1f, 0xb0, 0x0, 0x0, 0xe, 0xf0, - 0x1f, 0xb0, 0x0, 0x0, 0xc, 0xf0, 0x1f, 0xb0, - 0x0, 0x0, 0xe, 0xf0, 0x1f, 0xb0, 0x0, 0x0, - 0x9f, 0x90, 0x1f, 0xea, 0xaa, 0xbe, 0xfd, 0x10, - 0x1f, 0xff, 0xff, 0xfc, 0x70, 0x0, 0x1f, 0xb0, - 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, - 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x0, - 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x0, - - /* U+0051 "Q" */ - 0x0, 0x0, 0x4a, 0xdf, 0xeb, 0x50, 0x0, 0x0, - 0x0, 0xaf, 0xfc, 0xbc, 0xff, 0xc1, 0x0, 0x0, - 0xbf, 0xb2, 0x0, 0x1, 0xaf, 0xd0, 0x0, 0x6f, - 0xb0, 0x0, 0x0, 0x0, 0x9f, 0x80, 0xc, 0xf1, - 0x0, 0x0, 0x0, 0x0, 0xfe, 0x0, 0xfc, 0x0, - 0x0, 0x0, 0x0, 0xa, 0xf1, 0x1f, 0xa0, 0x0, - 0x0, 0x0, 0x0, 0x9f, 0x30, 0xfc, 0x0, 0x0, - 0x0, 0x0, 0xa, 0xf2, 0xd, 0xf1, 0x0, 0x0, - 0x0, 0x0, 0xfe, 0x0, 0x7f, 0xa0, 0x0, 0x0, - 0x0, 0x8f, 0x80, 0x0, 0xcf, 0xa1, 0x0, 0x0, - 0x9f, 0xd0, 0x0, 0x1, 0xcf, 0xfb, 0xab, 0xff, - 0xd1, 0x0, 0x0, 0x0, 0x6c, 0xef, 0xfd, 0x60, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x5f, 0xe6, 0x34, - 0xa7, 0x0, 0x0, 0x0, 0x0, 0x3c, 0xff, 0xfe, - 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, 0x43, 0x0, - - /* U+0052 "R" */ - 0x1f, 0xff, 0xff, 0xfc, 0x70, 0x0, 0x1f, 0xea, - 0xaa, 0xbe, 0xfd, 0x10, 0x1f, 0xb0, 0x0, 0x0, - 0x9f, 0x90, 0x1f, 0xb0, 0x0, 0x0, 0xe, 0xf0, - 0x1f, 0xb0, 0x0, 0x0, 0xc, 0xf0, 0x1f, 0xb0, - 0x0, 0x0, 0xe, 0xe0, 0x1f, 0xb0, 0x0, 0x0, - 0x9f, 0x90, 0x1f, 0xd9, 0x99, 0xae, 0xfd, 0x10, - 0x1f, 0xff, 0xff, 0xff, 0xa0, 0x0, 0x1f, 0xb0, - 0x0, 0x1f, 0xd0, 0x0, 0x1f, 0xb0, 0x0, 0x6, - 0xf9, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0xbf, 0x40, - 0x1f, 0xb0, 0x0, 0x0, 0x1e, 0xe0, - - /* U+0053 "S" */ - 0x0, 0x29, 0xdf, 0xfd, 0x81, 0x0, 0x3f, 0xfc, - 0x9a, 0xdf, 0xc0, 0xb, 0xf4, 0x0, 0x0, 0x23, - 0x0, 0xed, 0x0, 0x0, 0x0, 0x0, 0xc, 0xf3, - 0x0, 0x0, 0x0, 0x0, 0x5f, 0xfa, 0x61, 0x0, - 0x0, 0x0, 0x3b, 0xff, 0xfd, 0x70, 0x0, 0x0, - 0x0, 0x48, 0xef, 0xb0, 0x0, 0x0, 0x0, 0x0, - 0xbf, 0x40, 0x0, 0x0, 0x0, 0x6, 0xf6, 0xb, - 0x50, 0x0, 0x0, 0xcf, 0x31, 0xdf, 0xeb, 0x9a, - 0xef, 0x90, 0x0, 0x6b, 0xef, 0xeb, 0x50, 0x0, - - /* U+0054 "T" */ - 0xef, 0xff, 0xff, 0xff, 0xff, 0x89, 0xaa, 0xad, - 0xfb, 0xaa, 0xa5, 0x0, 0x0, 0x9f, 0x20, 0x0, - 0x0, 0x0, 0x9, 0xf2, 0x0, 0x0, 0x0, 0x0, - 0x9f, 0x20, 0x0, 0x0, 0x0, 0x9, 0xf2, 0x0, - 0x0, 0x0, 0x0, 0x9f, 0x20, 0x0, 0x0, 0x0, - 0x9, 0xf2, 0x0, 0x0, 0x0, 0x0, 0x9f, 0x20, - 0x0, 0x0, 0x0, 0x9, 0xf2, 0x0, 0x0, 0x0, - 0x0, 0x9f, 0x20, 0x0, 0x0, 0x0, 0x9, 0xf2, - 0x0, 0x0, 0x0, 0x0, 0x9f, 0x20, 0x0, 0x0, - - /* U+0055 "U" */ - 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, - 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, - 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf7, - 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, - 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, - 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf6, - 0x2f, 0xb0, 0x0, 0x0, 0x7, 0xf5, 0xe, 0xf0, - 0x0, 0x0, 0xb, 0xf2, 0x8, 0xfa, 0x0, 0x0, - 0x7f, 0xb0, 0x0, 0xcf, 0xfb, 0xbe, 0xfe, 0x20, - 0x0, 0x7, 0xcf, 0xfd, 0x81, 0x0, - - /* U+0056 "V" */ - 0xc, 0xf2, 0x0, 0x0, 0x0, 0x2, 0xf9, 0x6, - 0xf8, 0x0, 0x0, 0x0, 0x9, 0xf3, 0x0, 0xef, - 0x0, 0x0, 0x0, 0x1f, 0xc0, 0x0, 0x8f, 0x60, - 0x0, 0x0, 0x7f, 0x50, 0x0, 0x1f, 0xd0, 0x0, - 0x0, 0xee, 0x0, 0x0, 0xa, 0xf4, 0x0, 0x5, - 0xf7, 0x0, 0x0, 0x3, 0xfb, 0x0, 0xc, 0xf1, - 0x0, 0x0, 0x0, 0xdf, 0x20, 0x2f, 0xa0, 0x0, - 0x0, 0x0, 0x6f, 0x80, 0x9f, 0x30, 0x0, 0x0, - 0x0, 0xe, 0xe1, 0xfc, 0x0, 0x0, 0x0, 0x0, - 0x8, 0xfc, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x1, - 0xff, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xaf, - 0x80, 0x0, 0x0, - - /* U+0057 "W" */ - 0x4f, 0x90, 0x0, 0x0, 0xc, 0xf3, 0x0, 0x0, - 0x2, 0xf8, 0xe, 0xe0, 0x0, 0x0, 0x2f, 0xf8, - 0x0, 0x0, 0x8, 0xf3, 0x9, 0xf3, 0x0, 0x0, - 0x7f, 0xfd, 0x0, 0x0, 0xd, 0xe0, 0x4, 0xf8, - 0x0, 0x0, 0xcd, 0x8f, 0x20, 0x0, 0x2f, 0x80, - 0x0, 0xfe, 0x0, 0x2, 0xf8, 0x3f, 0x80, 0x0, - 0x7f, 0x30, 0x0, 0xaf, 0x30, 0x7, 0xf3, 0xe, - 0xd0, 0x0, 0xde, 0x0, 0x0, 0x5f, 0x80, 0xc, - 0xd0, 0x8, 0xf2, 0x2, 0xf9, 0x0, 0x0, 0xf, - 0xd0, 0x2f, 0x80, 0x3, 0xf7, 0x7, 0xf4, 0x0, - 0x0, 0xa, 0xf2, 0x7f, 0x30, 0x0, 0xed, 0xc, - 0xe0, 0x0, 0x0, 0x5, 0xf7, 0xde, 0x0, 0x0, - 0x9f, 0x4f, 0x90, 0x0, 0x0, 0x0, 0xfe, 0xf8, - 0x0, 0x0, 0x3f, 0xdf, 0x40, 0x0, 0x0, 0x0, - 0xbf, 0xf3, 0x0, 0x0, 0xe, 0xff, 0x0, 0x0, - 0x0, 0x0, 0x6f, 0xe0, 0x0, 0x0, 0x9, 0xfa, - 0x0, 0x0, - - /* U+0058 "X" */ - 0x2f, 0xd0, 0x0, 0x0, 0xb, 0xf3, 0x6, 0xfa, - 0x0, 0x0, 0x7f, 0x70, 0x0, 0xbf, 0x50, 0x2, - 0xfc, 0x0, 0x0, 0x1e, 0xe1, 0xd, 0xf2, 0x0, - 0x0, 0x5, 0xfb, 0x8f, 0x50, 0x0, 0x0, 0x0, - 0x9f, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xf5, - 0x0, 0x0, 0x0, 0x0, 0xdf, 0xfe, 0x10, 0x0, - 0x0, 0x9, 0xf6, 0x5f, 0xa0, 0x0, 0x0, 0x4f, - 0xb0, 0xa, 0xf6, 0x0, 0x1, 0xee, 0x10, 0x1, - 0xef, 0x20, 0xb, 0xf5, 0x0, 0x0, 0x4f, 0xc0, - 0x6f, 0xa0, 0x0, 0x0, 0x8, 0xf8, - - /* U+0059 "Y" */ - 0xc, 0xf2, 0x0, 0x0, 0x0, 0x5f, 0x60, 0x3f, - 0xb0, 0x0, 0x0, 0xe, 0xd0, 0x0, 0x9f, 0x50, - 0x0, 0x8, 0xf3, 0x0, 0x1, 0xee, 0x0, 0x2, - 0xfa, 0x0, 0x0, 0x6, 0xf8, 0x0, 0xbf, 0x10, - 0x0, 0x0, 0xc, 0xf1, 0x4f, 0x70, 0x0, 0x0, - 0x0, 0x3f, 0xbd, 0xd0, 0x0, 0x0, 0x0, 0x0, - 0xaf, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x2, 0xfc, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, - 0x0, 0x0, 0x0, 0x1, 0xfb, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x0, - 0x1, 0xfb, 0x0, 0x0, 0x0, - - /* U+005A "Z" */ - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xf1, 0xa, 0xaa, - 0xaa, 0xaa, 0xcf, 0xd0, 0x0, 0x0, 0x0, 0x1, - 0xef, 0x20, 0x0, 0x0, 0x0, 0xc, 0xf5, 0x0, - 0x0, 0x0, 0x0, 0x9f, 0x80, 0x0, 0x0, 0x0, - 0x5, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xe1, - 0x0, 0x0, 0x0, 0x0, 0xdf, 0x30, 0x0, 0x0, - 0x0, 0xa, 0xf6, 0x0, 0x0, 0x0, 0x0, 0x7f, - 0xa0, 0x0, 0x0, 0x0, 0x4, 0xfd, 0x0, 0x0, - 0x0, 0x0, 0x1e, 0xfb, 0xaa, 0xaa, 0xaa, 0xa2, - 0x3f, 0xff, 0xff, 0xff, 0xff, 0xf4, - - /* U+0061 "a" */ - 0x1, 0x7c, 0xff, 0xd6, 0x0, 0x9, 0xfc, 0x99, - 0xef, 0x80, 0x1, 0x30, 0x0, 0xd, 0xf0, 0x0, - 0x0, 0x0, 0x9, 0xf2, 0x1, 0x9e, 0xff, 0xff, - 0xf3, 0xa, 0xf8, 0x43, 0x3a, 0xf3, 0xf, 0xb0, - 0x0, 0x8, 0xf3, 0xf, 0xb0, 0x0, 0xe, 0xf3, - 0x9, 0xf9, 0x46, 0xdf, 0xf3, 0x0, 0x8d, 0xfe, - 0x87, 0xf3, - - /* U+0062 "b" */ - 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5, 0xf5, 0x0, - 0x0, 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, - 0x5, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x5f, 0x56, - 0xdf, 0xea, 0x20, 0x5, 0xfd, 0xfc, 0x9b, 0xff, - 0x30, 0x5f, 0xf5, 0x0, 0x4, 0xfe, 0x5, 0xfa, - 0x0, 0x0, 0x8, 0xf4, 0x5f, 0x60, 0x0, 0x0, - 0x4f, 0x75, 0xf6, 0x0, 0x0, 0x4, 0xf7, 0x5f, - 0xa0, 0x0, 0x0, 0x8f, 0x45, 0xff, 0x50, 0x0, - 0x4f, 0xe0, 0x5f, 0xcf, 0xc9, 0xbf, 0xf3, 0x5, - 0xf4, 0x6d, 0xfe, 0xa2, 0x0, - - /* U+0063 "c" */ - 0x0, 0x7, 0xdf, 0xeb, 0x30, 0x0, 0xcf, 0xd9, - 0xaf, 0xf4, 0x9, 0xf7, 0x0, 0x2, 0xc3, 0xf, - 0xd0, 0x0, 0x0, 0x0, 0x3f, 0x80, 0x0, 0x0, - 0x0, 0x3f, 0x80, 0x0, 0x0, 0x0, 0xf, 0xc0, - 0x0, 0x0, 0x0, 0x9, 0xf7, 0x0, 0x2, 0xc3, - 0x0, 0xcf, 0xd9, 0xaf, 0xf3, 0x0, 0x7, 0xdf, - 0xeb, 0x30, - - /* U+0064 "d" */ - 0x0, 0x0, 0x0, 0x0, 0x1f, 0xa0, 0x0, 0x0, - 0x0, 0x1, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x1f, - 0xa0, 0x0, 0x0, 0x0, 0x1, 0xfa, 0x0, 0x8, - 0xdf, 0xe8, 0x2f, 0xa0, 0x1d, 0xfd, 0x9b, 0xfd, - 0xfa, 0xa, 0xf8, 0x0, 0x2, 0xef, 0xa0, 0xfd, - 0x0, 0x0, 0x6, 0xfa, 0x3f, 0x80, 0x0, 0x0, - 0x2f, 0xa3, 0xf8, 0x0, 0x0, 0x2, 0xfa, 0xf, - 0xc0, 0x0, 0x0, 0x5f, 0xa0, 0xaf, 0x60, 0x0, - 0x1e, 0xfa, 0x1, 0xdf, 0xb7, 0x9e, 0xdf, 0xa0, - 0x0, 0x8d, 0xfe, 0x91, 0xfa, - - /* U+0065 "e" */ - 0x0, 0x8, 0xdf, 0xe9, 0x10, 0x0, 0x1d, 0xfb, - 0x8a, 0xfe, 0x20, 0xa, 0xf3, 0x0, 0x3, 0xfb, - 0x0, 0xfa, 0x0, 0x0, 0x9, 0xf1, 0x3f, 0xff, - 0xff, 0xff, 0xff, 0x33, 0xfa, 0x33, 0x33, 0x33, - 0x30, 0xf, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x9f, - 0x90, 0x0, 0x9, 0x10, 0x0, 0xdf, 0xda, 0xae, - 0xf6, 0x0, 0x0, 0x7d, 0xff, 0xc5, 0x0, - - /* U+0066 "f" */ - 0x0, 0x1a, 0xee, 0x90, 0xa, 0xf9, 0x88, 0x0, - 0xfb, 0x0, 0x0, 0x1f, 0x90, 0x0, 0xbf, 0xff, - 0xff, 0x55, 0x8f, 0xc7, 0x72, 0x1, 0xfa, 0x0, - 0x0, 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, - 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, 0x1f, - 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, 0x1f, 0xa0, - 0x0, - - /* U+0067 "g" */ - 0x0, 0x8, 0xdf, 0xe9, 0x1e, 0xc0, 0x1d, 0xfd, - 0x9b, 0xfe, 0xec, 0xa, 0xf8, 0x0, 0x1, 0xdf, - 0xc0, 0xfd, 0x0, 0x0, 0x4, 0xfc, 0x3f, 0x90, - 0x0, 0x0, 0xf, 0xc3, 0xf8, 0x0, 0x0, 0x0, - 0xfc, 0xf, 0xd0, 0x0, 0x0, 0x4f, 0xc0, 0xaf, - 0x80, 0x0, 0x1d, 0xfc, 0x1, 0xdf, 0xd9, 0xaf, - 0xdf, 0xc0, 0x0, 0x8d, 0xfe, 0x91, 0xfb, 0x0, - 0x0, 0x0, 0x0, 0x2f, 0x90, 0x27, 0x0, 0x0, - 0xb, 0xf4, 0x7, 0xff, 0xb9, 0xae, 0xfa, 0x0, - 0x4, 0xae, 0xff, 0xc6, 0x0, - - /* U+0068 "h" */ - 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5f, 0x50, 0x0, - 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5f, - 0x50, 0x0, 0x0, 0x0, 0x5f, 0x56, 0xdf, 0xea, - 0x10, 0x5f, 0xef, 0xca, 0xdf, 0xd0, 0x5f, 0xf4, - 0x0, 0xa, 0xf6, 0x5f, 0x90, 0x0, 0x2, 0xf9, - 0x5f, 0x60, 0x0, 0x0, 0xfa, 0x5f, 0x50, 0x0, - 0x0, 0xfb, 0x5f, 0x50, 0x0, 0x0, 0xfb, 0x5f, - 0x50, 0x0, 0x0, 0xfb, 0x5f, 0x50, 0x0, 0x0, - 0xfb, 0x5f, 0x50, 0x0, 0x0, 0xfb, - - /* U+0069 "i" */ - 0x6f, 0x69, 0xf9, 0x4, 0x0, 0x0, 0x5f, 0x55, - 0xf5, 0x5f, 0x55, 0xf5, 0x5f, 0x55, 0xf5, 0x5f, - 0x55, 0xf5, 0x5f, 0x55, 0xf5, - - /* U+006A "j" */ - 0x0, 0x4, 0xf7, 0x0, 0x7, 0xfa, 0x0, 0x0, - 0x40, 0x0, 0x0, 0x0, 0x0, 0x4, 0xf7, 0x0, - 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x4, 0xf7, - 0x0, 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x4, - 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, - 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x6, 0xf5, - 0x4b, 0x9f, 0xe1, 0x5e, 0xfc, 0x30, - - /* U+006B "k" */ - 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5, 0xf5, 0x0, - 0x0, 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, - 0x5, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x5f, 0x50, - 0x0, 0x1d, 0xf3, 0x5, 0xf5, 0x0, 0x2d, 0xf3, - 0x0, 0x5f, 0x50, 0x2e, 0xf4, 0x0, 0x5, 0xf5, - 0x2e, 0xf4, 0x0, 0x0, 0x5f, 0x9e, 0xfe, 0x0, - 0x0, 0x5, 0xff, 0xfa, 0xfa, 0x0, 0x0, 0x5f, - 0xe3, 0xc, 0xf6, 0x0, 0x5, 0xf6, 0x0, 0x1e, - 0xf3, 0x0, 0x5f, 0x50, 0x0, 0x3f, 0xd0, 0x5, - 0xf5, 0x0, 0x0, 0x7f, 0xa0, - - /* U+006C "l" */ - 0x5f, 0x55, 0xf5, 0x5f, 0x55, 0xf5, 0x5f, 0x55, - 0xf5, 0x5f, 0x55, 0xf5, 0x5f, 0x55, 0xf5, 0x5f, - 0x55, 0xf5, 0x5f, 0x55, 0xf5, - - /* U+006D "m" */ - 0x5f, 0x58, 0xdf, 0xe8, 0x0, 0x8d, 0xfe, 0x80, - 0x5, 0xfe, 0xfa, 0x9d, 0xfb, 0xdf, 0xa9, 0xdf, - 0xb0, 0x5f, 0xf2, 0x0, 0xd, 0xff, 0x30, 0x0, - 0xcf, 0x35, 0xf9, 0x0, 0x0, 0x7f, 0xa0, 0x0, - 0x6, 0xf6, 0x5f, 0x60, 0x0, 0x5, 0xf7, 0x0, - 0x0, 0x4f, 0x75, 0xf5, 0x0, 0x0, 0x5f, 0x60, - 0x0, 0x4, 0xf7, 0x5f, 0x50, 0x0, 0x5, 0xf6, - 0x0, 0x0, 0x4f, 0x75, 0xf5, 0x0, 0x0, 0x5f, - 0x60, 0x0, 0x4, 0xf7, 0x5f, 0x50, 0x0, 0x5, - 0xf6, 0x0, 0x0, 0x4f, 0x75, 0xf5, 0x0, 0x0, - 0x5f, 0x60, 0x0, 0x4, 0xf7, - - /* U+006E "n" */ - 0x5f, 0x57, 0xdf, 0xea, 0x10, 0x5f, 0xef, 0xa8, - 0xcf, 0xd0, 0x5f, 0xf3, 0x0, 0x9, 0xf6, 0x5f, - 0x90, 0x0, 0x2, 0xf9, 0x5f, 0x60, 0x0, 0x0, - 0xfa, 0x5f, 0x50, 0x0, 0x0, 0xfb, 0x5f, 0x50, - 0x0, 0x0, 0xfb, 0x5f, 0x50, 0x0, 0x0, 0xfb, - 0x5f, 0x50, 0x0, 0x0, 0xfb, 0x5f, 0x50, 0x0, - 0x0, 0xfb, - - /* U+006F "o" */ - 0x0, 0x7, 0xdf, 0xea, 0x30, 0x0, 0xd, 0xfd, - 0x9a, 0xff, 0x50, 0x9, 0xf7, 0x0, 0x2, 0xef, - 0x10, 0xfd, 0x0, 0x0, 0x6, 0xf7, 0x3f, 0x80, - 0x0, 0x0, 0x2f, 0x93, 0xf8, 0x0, 0x0, 0x2, - 0xf9, 0xf, 0xd0, 0x0, 0x0, 0x6f, 0x60, 0x9f, - 0x80, 0x0, 0x2e, 0xf1, 0x0, 0xcf, 0xd9, 0xaf, - 0xf4, 0x0, 0x0, 0x7d, 0xfe, 0xa3, 0x0, - - /* U+0070 "p" */ - 0x5f, 0x46, 0xdf, 0xea, 0x20, 0x5, 0xfd, 0xfa, - 0x8a, 0xff, 0x30, 0x5f, 0xf4, 0x0, 0x3, 0xfe, - 0x5, 0xfa, 0x0, 0x0, 0x8, 0xf4, 0x5f, 0x60, - 0x0, 0x0, 0x4f, 0x75, 0xf6, 0x0, 0x0, 0x4, - 0xf7, 0x5f, 0xa0, 0x0, 0x0, 0x9f, 0x45, 0xff, - 0x50, 0x0, 0x4f, 0xe0, 0x5f, 0xdf, 0xc9, 0xbf, - 0xf3, 0x5, 0xf5, 0x6d, 0xfe, 0xa2, 0x0, 0x5f, - 0x50, 0x0, 0x0, 0x0, 0x5, 0xf5, 0x0, 0x0, - 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5, - 0xf5, 0x0, 0x0, 0x0, 0x0, - - /* U+0071 "q" */ - 0x0, 0x8, 0xdf, 0xe8, 0x1f, 0xa0, 0x1d, 0xfd, - 0x9b, 0xfc, 0xfa, 0xa, 0xf7, 0x0, 0x2, 0xef, - 0xa0, 0xfd, 0x0, 0x0, 0x6, 0xfa, 0x3f, 0x80, - 0x0, 0x0, 0x2f, 0xa3, 0xf8, 0x0, 0x0, 0x2, - 0xfa, 0xf, 0xd0, 0x0, 0x0, 0x6f, 0xa0, 0xaf, - 0x80, 0x0, 0x2e, 0xfa, 0x1, 0xdf, 0xd9, 0xaf, - 0xdf, 0xa0, 0x0, 0x8d, 0xfe, 0x82, 0xfa, 0x0, - 0x0, 0x0, 0x0, 0x1f, 0xa0, 0x0, 0x0, 0x0, - 0x1, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xa0, - 0x0, 0x0, 0x0, 0x1, 0xfa, - - /* U+0072 "r" */ - 0x5f, 0x46, 0xdb, 0x5f, 0xcf, 0xd9, 0x5f, 0xf5, - 0x0, 0x5f, 0xa0, 0x0, 0x5f, 0x70, 0x0, 0x5f, - 0x50, 0x0, 0x5f, 0x50, 0x0, 0x5f, 0x50, 0x0, - 0x5f, 0x50, 0x0, 0x5f, 0x50, 0x0, - - /* U+0073 "s" */ - 0x1, 0x8d, 0xfe, 0xc7, 0x0, 0xcf, 0xb8, 0xad, - 0xd0, 0x3f, 0x90, 0x0, 0x1, 0x2, 0xfb, 0x0, - 0x0, 0x0, 0xb, 0xff, 0xb8, 0x40, 0x0, 0x5, - 0x9c, 0xff, 0xc0, 0x0, 0x0, 0x0, 0x9f, 0x60, - 0x50, 0x0, 0x5, 0xf7, 0x5f, 0xea, 0x9a, 0xfe, - 0x10, 0x6c, 0xef, 0xd9, 0x20, - - /* U+0074 "t" */ - 0x1, 0xfa, 0x0, 0x0, 0x1f, 0xa0, 0x0, 0xbf, - 0xff, 0xff, 0x55, 0x8f, 0xc7, 0x72, 0x1, 0xfa, - 0x0, 0x0, 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, - 0x0, 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, - 0xf, 0xc0, 0x0, 0x0, 0xbf, 0xa9, 0x90, 0x1, - 0xbe, 0xe9, - - /* U+0075 "u" */ - 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, - 0x3, 0xf8, 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, - 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, 0x3, - 0xf8, 0x7f, 0x40, 0x0, 0x4, 0xf8, 0x6f, 0x60, - 0x0, 0x6, 0xf8, 0x2f, 0xc0, 0x0, 0x1e, 0xf8, - 0xa, 0xfd, 0x89, 0xee, 0xf8, 0x0, 0x8d, 0xfe, - 0x92, 0xf8, - - /* U+0076 "v" */ - 0xd, 0xe0, 0x0, 0x0, 0xd, 0xd0, 0x6, 0xf6, - 0x0, 0x0, 0x3f, 0x70, 0x0, 0xfc, 0x0, 0x0, - 0xaf, 0x10, 0x0, 0x9f, 0x30, 0x1, 0xf9, 0x0, - 0x0, 0x2f, 0x90, 0x7, 0xf3, 0x0, 0x0, 0xb, - 0xf0, 0xe, 0xc0, 0x0, 0x0, 0x5, 0xf6, 0x5f, - 0x50, 0x0, 0x0, 0x0, 0xed, 0xbe, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xf8, 0x0, 0x0, 0x0, 0x0, - 0x1f, 0xf1, 0x0, 0x0, - - /* U+0077 "w" */ - 0xbe, 0x0, 0x0, 0xc, 0xf1, 0x0, 0x0, 0xae, - 0x5, 0xf4, 0x0, 0x2, 0xff, 0x60, 0x0, 0xf, - 0x80, 0xf, 0x90, 0x0, 0x8f, 0xeb, 0x0, 0x5, - 0xf2, 0x0, 0xae, 0x0, 0xd, 0xb8, 0xf1, 0x0, - 0xbd, 0x0, 0x4, 0xf4, 0x3, 0xf5, 0x2f, 0x70, - 0x1f, 0x70, 0x0, 0xe, 0xa0, 0x9e, 0x0, 0xcc, - 0x6, 0xf1, 0x0, 0x0, 0x9f, 0x1e, 0x90, 0x6, - 0xf2, 0xcc, 0x0, 0x0, 0x3, 0xfa, 0xf3, 0x0, - 0x1f, 0xaf, 0x60, 0x0, 0x0, 0xd, 0xfd, 0x0, - 0x0, 0xbf, 0xf1, 0x0, 0x0, 0x0, 0x8f, 0x70, - 0x0, 0x5, 0xfb, 0x0, 0x0, - - /* U+0078 "x" */ - 0x3f, 0xb0, 0x0, 0xc, 0xf2, 0x7, 0xf7, 0x0, - 0x7f, 0x60, 0x0, 0xbf, 0x33, 0xfa, 0x0, 0x0, - 0x1e, 0xde, 0xd0, 0x0, 0x0, 0x4, 0xff, 0x30, - 0x0, 0x0, 0x6, 0xff, 0x50, 0x0, 0x0, 0x3f, - 0xbc, 0xf2, 0x0, 0x0, 0xde, 0x12, 0xfc, 0x0, - 0xa, 0xf4, 0x0, 0x5f, 0x90, 0x6f, 0x80, 0x0, - 0xa, 0xf5, - - /* U+0079 "y" */ - 0xd, 0xe0, 0x0, 0x0, 0xd, 0xd0, 0x6, 0xf6, - 0x0, 0x0, 0x3f, 0x70, 0x0, 0xfc, 0x0, 0x0, - 0x9f, 0x10, 0x0, 0x9f, 0x30, 0x1, 0xfa, 0x0, - 0x0, 0x2f, 0x90, 0x6, 0xf3, 0x0, 0x0, 0xc, - 0xf0, 0xd, 0xc0, 0x0, 0x0, 0x5, 0xf6, 0x3f, - 0x60, 0x0, 0x0, 0x0, 0xed, 0xae, 0x0, 0x0, - 0x0, 0x0, 0x8f, 0xf8, 0x0, 0x0, 0x0, 0x0, - 0x1f, 0xf2, 0x0, 0x0, 0x0, 0x0, 0xf, 0xb0, - 0x0, 0x0, 0x1, 0x0, 0x7f, 0x40, 0x0, 0x0, - 0x1f, 0xaa, 0xfb, 0x0, 0x0, 0x0, 0x19, 0xee, - 0xa1, 0x0, 0x0, 0x0, - - /* U+007A "z" */ - 0x2f, 0xff, 0xff, 0xff, 0x91, 0x77, 0x77, 0x7e, - 0xf4, 0x0, 0x0, 0x6, 0xf8, 0x0, 0x0, 0x3, - 0xfc, 0x0, 0x0, 0x1, 0xee, 0x10, 0x0, 0x0, - 0xbf, 0x40, 0x0, 0x0, 0x8f, 0x70, 0x0, 0x0, - 0x4f, 0xb0, 0x0, 0x0, 0x1e, 0xf8, 0x77, 0x77, - 0x54, 0xff, 0xff, 0xff, 0xfb, - - /* U+00B0 "°" */ - 0x1, 0xaf, 0xd5, 0x0, 0xb8, 0x3, 0xe4, 0x1e, - 0x0, 0x6, 0xa2, 0xe0, 0x0, 0x6a, 0xc, 0x70, - 0x1d, 0x50, 0x2c, 0xff, 0x70, 0x0, 0x0, 0x0, - 0x0, - - /* U+00E9 "é" */ - 0x0, 0x0, 0x0, 0xcf, 0x40, 0x0, 0x0, 0x0, - 0xce, 0x20, 0x0, 0x0, 0x0, 0x58, 0x10, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x8, - 0xdf, 0xe9, 0x10, 0x0, 0x1d, 0xfb, 0x8a, 0xfe, - 0x20, 0xa, 0xf3, 0x0, 0x3, 0xfb, 0x0, 0xfa, - 0x0, 0x0, 0x9, 0xf1, 0x3f, 0xff, 0xff, 0xff, - 0xff, 0x33, 0xfa, 0x33, 0x33, 0x33, 0x30, 0xf, - 0xd0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0x90, 0x0, - 0x9, 0x10, 0x0, 0xdf, 0xda, 0xae, 0xf6, 0x0, - 0x0, 0x7d, 0xff, 0xc5, 0x0, - - /* U+00FB "û" */ - 0x0, 0x4, 0xff, 0x50, 0x0, 0x0, 0x3f, 0x87, - 0xf5, 0x0, 0x0, 0x75, 0x0, 0x47, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x7f, 0x40, 0x0, 0x3, - 0xf8, 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, - 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, 0x3, 0xf8, - 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, - 0x4, 0xf8, 0x6f, 0x60, 0x0, 0x6, 0xf8, 0x2f, - 0xc0, 0x0, 0x1e, 0xf8, 0xa, 0xfd, 0x89, 0xee, - 0xf8, 0x0, 0x8d, 0xfe, 0x92, 0xf8, - - /* U+F015 "" */ - 0x0, 0x0, 0x0, 0x0, 0xb, 0xd3, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1d, 0xff, - 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x3e, 0xff, 0xff, 0xf6, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x4f, 0xff, 0xff, 0xff, 0xf8, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x6f, 0xff, 0xff, 0xff, - 0xff, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xfc, 0x10, 0x0, 0x0, - 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfd, - 0x20, 0x1, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xfe, 0x30, 0xcf, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x2c, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xf2, 0x2, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0x31, 0x0, 0xb, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0, 0x0, 0xbf, - 0xff, 0xff, 0x96, 0x67, 0xff, 0xff, 0xff, 0x0, - 0x0, 0xb, 0xff, 0xff, 0xf0, 0x0, 0x9, 0xff, - 0xff, 0xf1, 0x0, 0x0, 0xbf, 0xff, 0xfe, 0x0, - 0x0, 0x9f, 0xff, 0xff, 0x10, 0x0, 0xb, 0xff, - 0xff, 0xe0, 0x0, 0x9, 0xff, 0xff, 0xf1, 0x0, - 0x0, 0xbf, 0xff, 0xfe, 0x0, 0x0, 0x9f, 0xff, - 0xff, 0x0, 0x0, 0x5, 0xff, 0xff, 0x80, 0x0, - 0x3, 0xff, 0xff, 0xa0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 -}; - - -/*--------------------- - * GLYPH DESCRIPTION - *--------------------*/ - -static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { - {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, - {.bitmap_index = 0, .adv_w = 77, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 0, .adv_w = 60, .box_w = 2, .box_h = 6, .ofs_x = 1, .ofs_y = 7}, - {.bitmap_index = 6, .adv_w = 65, .box_w = 4, .box_h = 3, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 12, .adv_w = 192, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 90, .adv_w = 107, .box_w = 5, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 123, .adv_w = 165, .box_w = 10, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 188, .adv_w = 165, .box_w = 10, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 253, .adv_w = 193, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 331, .adv_w = 165, .box_w = 10, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 396, .adv_w = 178, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 468, .adv_w = 172, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 540, .adv_w = 185, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 612, .adv_w = 178, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 684, .adv_w = 211, .box_w = 15, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 782, .adv_w = 218, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 860, .adv_w = 208, .box_w = 13, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 945, .adv_w = 238, .box_w = 13, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1030, .adv_w = 193, .box_w = 11, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1102, .adv_w = 183, .box_w = 10, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1167, .adv_w = 222, .box_w = 13, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1252, .adv_w = 234, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1330, .adv_w = 89, .box_w = 3, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1350, .adv_w = 148, .box_w = 9, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 1409, .adv_w = 207, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1487, .adv_w = 171, .box_w = 10, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1552, .adv_w = 275, .box_w = 15, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1650, .adv_w = 234, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1728, .adv_w = 242, .box_w = 15, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1826, .adv_w = 208, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1904, .adv_w = 242, .box_w = 15, .box_h = 16, .ofs_x = 0, .ofs_y = -3}, - {.bitmap_index = 2024, .adv_w = 209, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 2102, .adv_w = 179, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2174, .adv_w = 169, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2246, .adv_w = 228, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 2324, .adv_w = 205, .box_w = 14, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 2415, .adv_w = 324, .box_w = 20, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2545, .adv_w = 194, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2623, .adv_w = 186, .box_w = 13, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 2708, .adv_w = 189, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2786, .adv_w = 172, .box_w = 10, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2836, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 2913, .adv_w = 164, .box_w = 10, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 2963, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3040, .adv_w = 176, .box_w = 11, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3095, .adv_w = 102, .box_w = 7, .box_h = 14, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3144, .adv_w = 199, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = -4}, - {.bitmap_index = 3221, .adv_w = 196, .box_w = 10, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3291, .adv_w = 80, .box_w = 3, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3312, .adv_w = 82, .box_w = 6, .box_h = 18, .ofs_x = -2, .ofs_y = -4}, - {.bitmap_index = 3366, .adv_w = 177, .box_w = 11, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3443, .adv_w = 80, .box_w = 3, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3464, .adv_w = 304, .box_w = 17, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3549, .adv_w = 196, .box_w = 10, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3599, .adv_w = 183, .box_w = 11, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3654, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 1, .ofs_y = -4}, - {.bitmap_index = 3731, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = -4}, - {.bitmap_index = 3808, .adv_w = 118, .box_w = 6, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3838, .adv_w = 144, .box_w = 9, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3883, .adv_w = 119, .box_w = 7, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3925, .adv_w = 195, .box_w = 10, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3975, .adv_w = 161, .box_w = 12, .box_h = 10, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 4035, .adv_w = 259, .box_w = 17, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 4120, .adv_w = 159, .box_w = 10, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 4170, .adv_w = 161, .box_w = 12, .box_h = 14, .ofs_x = -1, .ofs_y = -4}, - {.bitmap_index = 4254, .adv_w = 150, .box_w = 9, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 4299, .adv_w = 121, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 6}, - {.bitmap_index = 4324, .adv_w = 176, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 4401, .adv_w = 195, .box_w = 10, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 4471, .adv_w = 324, .box_w = 21, .box_h = 19, .ofs_x = 0, .ofs_y = -3} -}; - -/*--------------------- - * CHARACTER MAPPING - *--------------------*/ - -static const uint16_t unicode_list_0[] = { - 0x0, 0x7, 0xe -}; - -static const uint16_t unicode_list_4[] = { - 0x0, 0x39, 0x4b, 0xef65 -}; - -/*Collect the unicode lists and glyph_id offsets*/ -static const lv_font_fmt_txt_cmap_t cmaps[] = -{ - { - .range_start = 32, .range_length = 15, .glyph_id_start = 1, - .unicode_list = unicode_list_0, .glyph_id_ofs_list = NULL, .list_length = 3, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - }, - { - .range_start = 48, .range_length = 10, .glyph_id_start = 4, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 65, .range_length = 26, .glyph_id_start = 14, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 97, .range_length = 26, .glyph_id_start = 40, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 176, .range_length = 61286, .glyph_id_start = 66, - .unicode_list = unicode_list_4, .glyph_id_ofs_list = NULL, .list_length = 4, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - } -}; - -/*----------------- - * KERNING - *----------------*/ - - -/*Map glyph_ids to kern left classes*/ -static const uint8_t kern_left_class_mapping[] = -{ - 0, 0, 1, 2, 3, 0, 4, 5, - 6, 7, 8, 9, 10, 3, 11, 12, - 13, 14, 15, 16, 17, 18, 18, 19, - 20, 21, 18, 18, 14, 22, 14, 23, - 24, 25, 19, 26, 26, 27, 28, 29, - 30, 31, 32, 33, 34, 35, 36, 30, - 36, 36, 37, 33, 30, 30, 31, 31, - 38, 39, 40, 41, 36, 42, 42, 43, - 42, 44, 45, 34, 36, 0 -}; - -/*Map glyph_ids to kern right classes*/ -static const uint8_t kern_right_class_mapping[] = -{ - 0, 0, 1, 2, 3, 4, 5, 6, - 7, 8, 3, 9, 10, 11, 12, 13, - 14, 13, 13, 13, 14, 13, 13, 15, - 13, 13, 13, 13, 14, 13, 14, 13, - 16, 17, 18, 19, 19, 20, 21, 22, - 23, 24, 25, 25, 25, 0, 25, 24, - 26, 27, 24, 24, 28, 28, 25, 28, - 25, 28, 29, 30, 31, 32, 32, 33, - 32, 34, 35, 25, 31, 0 -}; - -/*Kern values between classes*/ -static const int8_t kern_class_values[] = -{ - 13, -16, 2, 14, 6, 5, -12, 2, - 14, 1, 12, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 6, -16, 0, -3, -4, 3, - 3, -3, 0, -4, 3, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -18, 2, -3, - 0, -1, -1, -3, 0, 0, -2, 0, - 0, -2, 0, 0, -7, 0, -6, 0, - -7, -10, -10, -5, 0, 0, 0, 0, - -2, 0, 0, 3, 0, 2, -3, 0, - 1, 0, 3, -1, 0, 0, 0, -5, - 0, -1, 0, 0, 1, 0, 0, 4, - 0, -2, 0, -3, 0, -5, 0, 0, - 0, -3, 0, 0, 0, 0, 0, -1, - 1, -2, -2, 0, -3, 0, 0, 0, - -1, -1, 0, -3, -3, 0, 0, 1, - 0, 0, 0, 0, -2, 0, -3, -3, - -3, 0, 0, 0, 0, 0, -2, 0, - 0, 0, 0, -2, -4, 0, -4, -9, - 6, 0, -7, -1, -3, 0, -1, -14, - 3, -2, 0, 0, 3, 1, -2, -15, - 0, -15, -2, -25, -2, 8, 0, 4, - 0, 0, 0, 0, 1, 0, -5, -4, - 0, -9, 0, 0, 0, 0, -1, -1, - 0, -1, -4, 0, 0, 0, 0, 0, - -3, 0, -3, 0, -2, -3, -2, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -2, -2, 0, -3, -2, 3, 0, - 0, 0, 0, 0, 0, -2, 0, 0, - 2, 0, 0, 0, 0, -3, 0, -3, - -2, -3, 0, 0, 0, 2, 0, -2, - 0, 0, 0, 0, -3, -4, 0, -5, - 9, -15, -6, 3, 0, -2, -19, -5, - 0, -5, 0, -18, 0, -5, -8, -2, - 0, 0, 1, -1, 2, -2, -11, 0, - -14, -7, -6, -7, -9, -3, -8, -1, - -5, -8, 2, 1, 3, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -1, 0, - 0, -1, 0, -3, 0, -5, -6, -6, - -1, 0, 0, 0, 0, -2, 0, 0, - 0, 0, 1, -2, 0, 0, -12, 10, - -2, -12, 0, 3, -4, 0, -14, -1, - -4, 4, 0, -3, 4, 0, -10, -4, - -11, -10, -12, 0, 0, 0, -1, 0, - 0, 0, -1, -1, -3, -8, -10, -1, - -27, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -3, 0, -1, -3, -4, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, -6, 3, - -2, -1, -7, -3, 0, -4, -3, -5, - 0, -4, 0, -1, -2, -1, -2, -5, - -3, 0, -2, 0, -6, 0, 0, 0, - -6, 0, -5, 0, -5, -5, 3, -5, - -6, 0, -3, -3, -3, 0, 0, 0, - 0, 0, -3, 0, 0, -4, 0, -3, - 0, -6, -7, -9, -2, 0, 0, 0, - 0, 23, 0, 0, 1, 0, 0, -4, - 0, 3, 0, 3, -4, 0, -2, -3, - -9, -2, -2, -2, -1, 0, 0, -1, - 0, 0, 0, 0, -3, -2, -2, 0, - -2, 0, -2, 0, 0, 0, -2, -3, - -2, -3, -3, -3, 0, 12, -3, -4, - 4, 0, 0, -14, -5, 3, -5, 2, - -9, 0, -2, -4, -1, 1, 0, 0, - -5, 0, 0, -5, 0, -5, -3, -4, - -3, -3, 0, -5, 1, -5, -5, 9, - 0, 3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -2, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, -2, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -4, 0, 0, 0, 0, -4, 0, - 0, -3, -3, 0, 0, 0, 0, 0, - -1, 0, 0, 0, 0, 0, -2, 0, - 0, 0, 0, -6, 6, 1, -2, -14, - 0, 0, -6, -3, -8, 0, -7, 0, - -4, -12, -3, -12, -11, -14, 0, -4, - 0, -7, -3, -1, -3, -5, -8, -5, - -11, -12, -7, -3, 0, 9, -6, -11, - 0, 1, -9, 0, -14, -2, -3, 1, - 0, -4, 0, -2, -19, -3, -15, -3, - -21, 0, 1, 0, -2, 0, 0, 0, - 0, -1, -2, -11, -2, 0, -19, 0, - -8, 0, 0, -1, -4, -9, -3, 0, - -2, 0, -13, -3, 0, -10, 0, -9, - -2, -5, -7, -3, -5, -4, 0, -3, - -5, -3, -5, 0, 1, 0, -2, -10, - 0, 6, 0, 0, 0, 0, 0, -2, - -6, 0, 0, 0, 0, 0, 0, 0, - -3, 0, -3, 0, 0, -6, -3, 0, - -1, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 4, -9, 6, 0, - -3, 0, -2, 3, 0, -3, 0, -3, - 0, 0, 0, 0, 0, -3, 0, 0, - -4, -4, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -3, -3, 0, -4, - 2, -9, -6, 12, 5, 3, -25, -2, - 6, -3, 0, -10, 0, -3, -3, -3, - 3, -4, -2, -9, -2, 0, -8, 0, - -16, -4, 8, -4, -11, 1, -4, -10, - -10, -3, 12, 0, -11, -7, 9, 0, - 1, -21, -2, 3, -5, -2, -11, -4, - -6, -4, -4, -2, 0, 0, -7, -6, - -3, -16, 0, -16, -4, 0, -10, -17, - -1, -9, -5, -10, -8, 8, 0, 0, - -10, 3, 0, 0, -15, 0, -3, -6, - -5, -10, -7, -7, 0, -4, -9, -3, - -7, -5, -9, -3, -5, 0, -9, -3, - 0, -3, -6, -7, -8, -8, -11, -4, - -6, 0, -11, -10, 10, -3, 1, -27, - -5, 6, -6, -5, -12, -3, -9, -3, - -4, -2, -3, -6, -9, -1, 0, -19, - 0, -17, -7, 7, -11, -20, -6, -10, - -12, -14, -10, 6, 0, 6, -5, 6, - 0, 0, -9, -1, 0, -1, 0, 0, - 0, -2, 0, 0, 0, 0, 0, -3, - 0, 0, 1, 0, -3, 0, 0, 0, - 0, -2, -2, -3, 0, 0, 0, 0, - 0, 0, -6, -1, 0, 0, 0, -6, - 0, -3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, -3, 0, - 0, -5, -4, -3, 0, -8, -3, -7, - 0, 0, -8, 0, -3, -3, 0, 0, - 0, 0, -23, -5, -12, -3, -10, 0, - -1, 0, 0, 0, 0, 0, 0, 0, - 0, -4, -5, -2, -5, 0, 6, -2, - -7, -2, -5, -5, 0, -3, -1, -2, - 0, 0, -1, 0, 0, -25, -2, -4, - 0, -6, 0, 0, -2, -2, 0, 0, - 0, 0, 2, 0, -2, -5, -2, 5, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, 0, 0, - 0, 0, 0, -6, 0, 0, -8, -3, - -6, 0, 0, -8, 0, -3, 0, 0, - 0, 0, 0, -28, 0, -6, -11, -14, - 0, -4, 0, 0, 0, 0, 0, 0, - 0, 0, -3, -4, -1, -4, 0, -3, - 3, 14, 5, 6, -8, 3, 12, 3, - 8, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -3, 0, -2, 23, - 12, 23, 0, 0, 0, 3, 0, 0, - 11, 0, 0, 0, -2, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -5, -24, -3, -2, -12, -14, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 3, -3, 2, - 5, 3, -9, 0, -1, -2, 3, 0, - 0, 0, 0, 0, -7, 0, -3, -2, - -6, 0, -3, 0, -6, -2, 0, -2, - -5, 0, -3, -8, -6, -3, 0, 0, - 0, 0, -2, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -5, -24, - -3, -2, -12, -14, 0, 0, 0, 0, - 0, 14, 0, 0, 0, 0, 0, 0, - 0, 0, 0, -3, 1, -2, 1, -2, - -8, 1, 6, 1, 2, -12, -3, -7, - 0, -5, -11, -5, -8, -12, -11, 0, - -2, -2, -3, -2, 0, -2, -1, 4, - 0, 4, -2, 0, 9, 0, 0, 0, - -2, -3, -3, 0, 0, -8, 0, -1, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -3, -3, 0, -4, - 0, 3, -5, -5, -2, 0, -8, -2, - -6, -2, -3, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -5, 0, 0, 0, 0, -4, 0, -3, - 0, 0, -1, 0, -10, 2, 3, 3, - -1, -8, 2, 4, 2, 9, -8, 0, - -2, 0, -2, -12, 0, 0, -9, -8, - 0, -5, 0, -4, 0, -4, 0, -2, - 4, 0, -2, -9, -3, 11, 0, 0, - -3, 2, 0, 0, -10, 0, -2, -1, - 0, 0, 0, -2, 0, -3, -12, -3, - -6, 0, -9, 0, -3, 0, -5, 0, - 2, 0, -3, 0, -3, -9, 0, -3, - 3, 0, 1, 0, -3, -2, 0, -3, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -2, 0, 0, 0, 0, 1, 0, - -3, -3, 0, 0, 6, -18, 1, 12, - 9, 5, -12, 2, 12, 0, 11, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0 -}; - - -/*Collect the kern class' data in one place*/ -static const lv_font_fmt_txt_kern_classes_t kern_classes = -{ - .class_pair_values = kern_class_values, - .left_class_mapping = kern_left_class_mapping, - .right_class_mapping = kern_right_class_mapping, - .left_class_cnt = 45, - .right_class_cnt = 35, -}; - -/*-------------------- - * ALL CUSTOM DATA - *--------------------*/ - -#if LVGL_VERSION_MAJOR == 8 -/*Store all the custom data of the font*/ -static lv_font_fmt_txt_glyph_cache_t cache; -#endif - -#if LVGL_VERSION_MAJOR >= 8 -static const lv_font_fmt_txt_dsc_t font_dsc = { -#else -static lv_font_fmt_txt_dsc_t font_dsc = { -#endif - .glyph_bitmap = glyph_bitmap, - .glyph_dsc = glyph_dsc, - .cmaps = cmaps, - .kern_dsc = &kern_classes, - .kern_scale = 16, - .cmap_num = 5, - .bpp = 4, - .kern_classes = 1, - .bitmap_format = 0, -#if LVGL_VERSION_MAJOR == 8 - .cache = &cache -#endif -}; - - - -/*----------------- - * PUBLIC FONT - *----------------*/ - -/*Initialize a public general font descriptor*/ -#if LVGL_VERSION_MAJOR >= 8 -const lv_font_t montserrat_medium_18 = { -#else -lv_font_t montserrat_medium_18 = { -#endif - .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ - .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ - .line_height = 20, /*The maximum line height required by the font*/ - .base_line = 4, /*Baseline measured from the bottom of the line*/ -#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) - .subpx = LV_FONT_SUBPX_NONE, -#endif -#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 - .underline_position = -1, - .underline_thickness = 1, -#endif - .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ -#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 - .fallback = NULL, -#endif - .user_data = NULL, -}; - - - -#endif /*#if MONTSERRAT_MEDIUM_18*/ - +/******************************************************************************* + * Size: 18 px + * Bpp: 4 + * Opts: --bpp 4 --size 18 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°éûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz:- ' --format lvgl -o montserrat_medium_18.c --font fa-solid-900.ttf --range 61461,0xf0c2 + ******************************************************************************/ + +#ifdef LV_LVGL_H_INCLUDE_SIMPLE +#include "lvgl.h" +#else +#include "lvgl/lvgl.h" +#endif + +#ifndef MONTSERRAT_MEDIUM_18 +#define MONTSERRAT_MEDIUM_18 1 +#endif + +#if MONTSERRAT_MEDIUM_18 + +/*----------------- + * BITMAPS + *----------------*/ + +/*Store the image of the glyphs*/ +static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { + /* U+0020 " " */ + + /* U+0027 "'" */ + 0xda, 0xd9, 0xd9, 0xc8, 0xc8, 0x0, + + /* U+002D "-" */ + 0x88, 0x88, 0x7f, 0xff, 0xfe, + + /* U+002E "." */ + 0x5, 0x60, 0x1f, 0xf2, 0xc, 0xd0, + + /* U+0030 "0" */ + 0x0, 0x4, 0xbe, 0xeb, 0x40, 0x0, 0x0, 0x6f, + 0xfb, 0xbf, 0xf6, 0x0, 0x2, 0xfd, 0x10, 0x1, + 0xdf, 0x20, 0xa, 0xf3, 0x0, 0x0, 0x3f, 0x90, + 0xe, 0xe0, 0x0, 0x0, 0xe, 0xe0, 0xf, 0xb0, + 0x0, 0x0, 0xb, 0xf0, 0x1f, 0xa0, 0x0, 0x0, + 0xa, 0xf1, 0xf, 0xb0, 0x0, 0x0, 0xb, 0xf0, + 0xe, 0xe0, 0x0, 0x0, 0xe, 0xe0, 0x9, 0xf3, + 0x0, 0x0, 0x3f, 0x90, 0x2, 0xfd, 0x10, 0x1, + 0xdf, 0x20, 0x0, 0x6f, 0xfb, 0xbf, 0xf6, 0x0, + 0x0, 0x4, 0xbe, 0xeb, 0x40, 0x0, + + /* U+0031 "1" */ + 0xdf, 0xff, 0xc8, 0xaa, 0xfc, 0x0, 0xf, 0xc0, + 0x0, 0xfc, 0x0, 0xf, 0xc0, 0x0, 0xfc, 0x0, + 0xf, 0xc0, 0x0, 0xfc, 0x0, 0xf, 0xc0, 0x0, + 0xfc, 0x0, 0xf, 0xc0, 0x0, 0xfc, 0x0, 0xf, + 0xc0, + + /* U+0032 "2" */ + 0x1, 0x8d, 0xfe, 0xc5, 0x0, 0x4f, 0xfd, 0xac, + 0xff, 0x70, 0x3c, 0x30, 0x0, 0x2f, 0xf0, 0x0, + 0x0, 0x0, 0xb, 0xf2, 0x0, 0x0, 0x0, 0xc, + 0xf1, 0x0, 0x0, 0x0, 0x3f, 0xb0, 0x0, 0x0, + 0x2, 0xee, 0x20, 0x0, 0x0, 0x2e, 0xf3, 0x0, + 0x0, 0x2, 0xef, 0x30, 0x0, 0x0, 0x2e, 0xf3, + 0x0, 0x0, 0x2, 0xef, 0x30, 0x0, 0x0, 0x2e, + 0xfc, 0xaa, 0xaa, 0xa7, 0x5f, 0xff, 0xff, 0xff, + 0xfb, + + /* U+0033 "3" */ + 0x5f, 0xff, 0xff, 0xff, 0xf0, 0x3a, 0xaa, 0xaa, + 0xcf, 0xc0, 0x0, 0x0, 0x1, 0xee, 0x10, 0x0, + 0x0, 0xc, 0xf3, 0x0, 0x0, 0x0, 0x9f, 0x60, + 0x0, 0x0, 0x4, 0xfe, 0x61, 0x0, 0x0, 0x5, + 0xdf, 0xff, 0x50, 0x0, 0x0, 0x0, 0x3e, 0xf2, + 0x0, 0x0, 0x0, 0x7, 0xf6, 0x0, 0x0, 0x0, + 0x6, 0xf6, 0x69, 0x10, 0x0, 0x1d, 0xf2, 0x9f, + 0xfc, 0xbc, 0xff, 0x80, 0x4, 0xae, 0xfe, 0xb5, + 0x0, + + /* U+0034 "4" */ + 0x0, 0x0, 0x0, 0x4f, 0xa0, 0x0, 0x0, 0x0, + 0x1, 0xed, 0x0, 0x0, 0x0, 0x0, 0xc, 0xf2, + 0x0, 0x0, 0x0, 0x0, 0x9f, 0x50, 0x0, 0x0, + 0x0, 0x5, 0xf9, 0x0, 0x0, 0x0, 0x0, 0x2f, + 0xc0, 0x3, 0xc5, 0x0, 0x0, 0xde, 0x10, 0x4, + 0xf7, 0x0, 0xb, 0xf4, 0x0, 0x4, 0xf7, 0x0, + 0x4f, 0xff, 0xff, 0xff, 0xff, 0xfd, 0x39, 0x99, + 0x99, 0x9b, 0xfc, 0x98, 0x0, 0x0, 0x0, 0x5, + 0xf7, 0x0, 0x0, 0x0, 0x0, 0x5, 0xf7, 0x0, + 0x0, 0x0, 0x0, 0x5, 0xf7, 0x0, + + /* U+0035 "5" */ + 0x2, 0xff, 0xff, 0xff, 0xf0, 0x4, 0xfc, 0xaa, + 0xaa, 0xa0, 0x5, 0xf5, 0x0, 0x0, 0x0, 0x7, + 0xf3, 0x0, 0x0, 0x0, 0x9, 0xf1, 0x0, 0x0, + 0x0, 0xa, 0xff, 0xff, 0xc7, 0x0, 0x7, 0xaa, + 0xab, 0xff, 0xc0, 0x0, 0x0, 0x0, 0xb, 0xf6, + 0x0, 0x0, 0x0, 0x3, 0xfa, 0x0, 0x0, 0x0, + 0x3, 0xfa, 0x2c, 0x20, 0x0, 0xb, 0xf6, 0x6f, + 0xfd, 0xbb, 0xef, 0xb0, 0x3, 0x9d, 0xff, 0xc7, + 0x0, + + /* U+0036 "6" */ + 0x0, 0x1, 0x8d, 0xfe, 0xc6, 0x0, 0x4, 0xef, + 0xca, 0xad, 0x90, 0x1, 0xee, 0x40, 0x0, 0x0, + 0x0, 0x8f, 0x40, 0x0, 0x0, 0x0, 0xe, 0xe0, + 0x0, 0x0, 0x0, 0x0, 0xfb, 0x2a, 0xef, 0xd7, + 0x0, 0x1f, 0xdf, 0xd9, 0x9d, 0xfb, 0x1, 0xff, + 0xa0, 0x0, 0xa, 0xf5, 0xf, 0xf2, 0x0, 0x0, + 0x3f, 0x90, 0xbf, 0x20, 0x0, 0x3, 0xf8, 0x4, + 0xfa, 0x0, 0x0, 0xaf, 0x40, 0x9, 0xfd, 0x99, + 0xdf, 0xa0, 0x0, 0x5, 0xcf, 0xfc, 0x60, 0x0, + + /* U+0037 "7" */ + 0x7f, 0xff, 0xff, 0xff, 0xff, 0x7, 0xfb, 0xaa, + 0xaa, 0xaf, 0xe0, 0x7f, 0x40, 0x0, 0x5, 0xf8, + 0x6, 0xf4, 0x0, 0x0, 0xcf, 0x10, 0x0, 0x0, + 0x0, 0x3f, 0xa0, 0x0, 0x0, 0x0, 0xa, 0xf3, + 0x0, 0x0, 0x0, 0x1, 0xfc, 0x0, 0x0, 0x0, + 0x0, 0x8f, 0x50, 0x0, 0x0, 0x0, 0xe, 0xe0, + 0x0, 0x0, 0x0, 0x6, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0xdf, 0x10, 0x0, 0x0, 0x0, 0x4f, 0x90, + 0x0, 0x0, 0x0, 0xb, 0xf2, 0x0, 0x0, 0x0, + + /* U+0038 "8" */ + 0x0, 0x2a, 0xef, 0xfc, 0x70, 0x0, 0x3f, 0xfb, + 0x89, 0xdf, 0xb0, 0xa, 0xf5, 0x0, 0x0, 0xbf, + 0x30, 0xbf, 0x10, 0x0, 0x8, 0xf4, 0x4, 0xfc, + 0x42, 0x26, 0xfd, 0x0, 0x6, 0xff, 0xff, 0xfe, + 0x10, 0x5, 0xfe, 0x85, 0x6a, 0xfd, 0x10, 0xee, + 0x10, 0x0, 0x7, 0xf8, 0x2f, 0xa0, 0x0, 0x0, + 0x1f, 0xb2, 0xfb, 0x0, 0x0, 0x2, 0xfb, 0xd, + 0xf4, 0x0, 0x0, 0xaf, 0x70, 0x3f, 0xfb, 0x89, + 0xdf, 0xc0, 0x0, 0x29, 0xdf, 0xfc, 0x60, 0x0, + + /* U+0039 "9" */ + 0x0, 0x6c, 0xff, 0xc6, 0x0, 0x0, 0xaf, 0xd9, + 0x8c, 0xfa, 0x0, 0x3f, 0xb0, 0x0, 0x7, 0xf6, + 0x7, 0xf5, 0x0, 0x0, 0xf, 0xd0, 0x6f, 0x60, + 0x0, 0x2, 0xff, 0x11, 0xff, 0x51, 0x4, 0xdf, + 0xf2, 0x4, 0xef, 0xff, 0xfb, 0x9f, 0x30, 0x0, + 0x57, 0x73, 0xa, 0xf1, 0x0, 0x0, 0x0, 0x0, + 0xdf, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xa0, 0x0, + 0x0, 0x0, 0x3e, 0xf2, 0x0, 0x8e, 0xba, 0xcf, + 0xf5, 0x0, 0x5, 0xbe, 0xfd, 0x92, 0x0, 0x0, + + /* U+003A ":" */ + 0xc, 0xd0, 0x1f, 0xf2, 0x5, 0x60, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x5, 0x60, + 0x1f, 0xf2, 0xc, 0xd0, + + /* U+0041 "A" */ + 0x0, 0x0, 0x0, 0x8f, 0xa0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xe, 0xff, 0x20, 0x0, 0x0, 0x0, + 0x0, 0x6, 0xf6, 0xf9, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xdd, 0xb, 0xf0, 0x0, 0x0, 0x0, 0x0, + 0x4f, 0x60, 0x4f, 0x70, 0x0, 0x0, 0x0, 0xb, + 0xe0, 0x0, 0xdd, 0x0, 0x0, 0x0, 0x2, 0xf8, + 0x0, 0x6, 0xf5, 0x0, 0x0, 0x0, 0x9f, 0x10, + 0x0, 0xe, 0xc0, 0x0, 0x0, 0x1f, 0xff, 0xff, + 0xff, 0xff, 0x30, 0x0, 0x7, 0xf8, 0x88, 0x88, + 0x88, 0xfa, 0x0, 0x0, 0xed, 0x0, 0x0, 0x0, + 0xb, 0xf1, 0x0, 0x5f, 0x60, 0x0, 0x0, 0x0, + 0x4f, 0x80, 0xc, 0xf1, 0x0, 0x0, 0x0, 0x0, + 0xee, 0x0, + + /* U+0042 "B" */ + 0x1f, 0xff, 0xff, 0xfe, 0xb4, 0x0, 0x1f, 0xd8, + 0x88, 0x8a, 0xff, 0x70, 0x1f, 0xb0, 0x0, 0x0, + 0x2f, 0xf0, 0x1f, 0xb0, 0x0, 0x0, 0xc, 0xf0, + 0x1f, 0xb0, 0x0, 0x0, 0x2f, 0xc0, 0x1f, 0xd8, + 0x88, 0x8a, 0xfe, 0x30, 0x1f, 0xff, 0xff, 0xff, + 0xfd, 0x40, 0x1f, 0xb0, 0x0, 0x1, 0x4d, 0xf3, + 0x1f, 0xb0, 0x0, 0x0, 0x4, 0xf9, 0x1f, 0xb0, + 0x0, 0x0, 0x2, 0xfb, 0x1f, 0xb0, 0x0, 0x0, + 0x8, 0xf8, 0x1f, 0xd8, 0x88, 0x89, 0xcf, 0xe1, + 0x1f, 0xff, 0xff, 0xff, 0xd9, 0x10, + + /* U+0043 "C" */ + 0x0, 0x0, 0x4a, 0xef, 0xeb, 0x50, 0x0, 0x1, + 0xbf, 0xfc, 0xac, 0xff, 0xb0, 0x0, 0xbf, 0xb2, + 0x0, 0x1, 0x9c, 0x0, 0x6f, 0xb0, 0x0, 0x0, + 0x0, 0x0, 0xd, 0xf1, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, + 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xfc, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xd, 0xf1, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6f, 0xb0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xbf, 0xb2, 0x0, 0x1, 0xac, 0x10, + 0x1, 0xbf, 0xfc, 0xbc, 0xff, 0xb0, 0x0, 0x0, + 0x4b, 0xef, 0xeb, 0x50, 0x0, + + /* U+0044 "D" */ + 0x1f, 0xff, 0xff, 0xfd, 0xa4, 0x0, 0x1, 0xfe, + 0xaa, 0xaa, 0xcf, 0xfa, 0x0, 0x1f, 0xb0, 0x0, + 0x0, 0x2b, 0xfa, 0x1, 0xfb, 0x0, 0x0, 0x0, + 0xc, 0xf4, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x3f, + 0xb1, 0xfb, 0x0, 0x0, 0x0, 0x0, 0xee, 0x1f, + 0xb0, 0x0, 0x0, 0x0, 0xd, 0xf1, 0xfb, 0x0, + 0x0, 0x0, 0x0, 0xee, 0x1f, 0xb0, 0x0, 0x0, + 0x0, 0x3f, 0xb1, 0xfb, 0x0, 0x0, 0x0, 0xc, + 0xf4, 0x1f, 0xb0, 0x0, 0x0, 0x2b, 0xfa, 0x1, + 0xfe, 0xaa, 0xaa, 0xcf, 0xfa, 0x0, 0x1f, 0xff, + 0xff, 0xfd, 0xa4, 0x0, 0x0, + + /* U+0045 "E" */ + 0x1f, 0xff, 0xff, 0xff, 0xfc, 0x1, 0xfe, 0xaa, + 0xaa, 0xaa, 0x70, 0x1f, 0xb0, 0x0, 0x0, 0x0, + 0x1, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, + 0x0, 0x0, 0x0, 0x1, 0xfd, 0x99, 0x99, 0x99, + 0x0, 0x1f, 0xff, 0xff, 0xff, 0xf0, 0x1, 0xfb, + 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, + 0x0, 0x1, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x1f, + 0xb0, 0x0, 0x0, 0x0, 0x1, 0xfe, 0xaa, 0xaa, + 0xaa, 0xa0, 0x1f, 0xff, 0xff, 0xff, 0xff, 0x0, + + /* U+0046 "F" */ + 0x1f, 0xff, 0xff, 0xff, 0xfc, 0x1f, 0xea, 0xaa, + 0xaa, 0xa7, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, + 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, + 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xff, + 0xff, 0xff, 0xf0, 0x1f, 0xe9, 0x99, 0x99, 0x90, + 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, + 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, + 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, + 0x0, + + /* U+0047 "G" */ + 0x0, 0x0, 0x4a, 0xdf, 0xeb, 0x60, 0x0, 0x1, + 0xbf, 0xfc, 0xbb, 0xff, 0xc1, 0x0, 0xbf, 0xb2, + 0x0, 0x0, 0x7d, 0x10, 0x6f, 0xb0, 0x0, 0x0, + 0x0, 0x0, 0xd, 0xf1, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, + 0xa0, 0x0, 0x0, 0x0, 0x39, 0x30, 0xfc, 0x0, + 0x0, 0x0, 0x6, 0xf5, 0xc, 0xf1, 0x0, 0x0, + 0x0, 0x6f, 0x50, 0x6f, 0xb0, 0x0, 0x0, 0x6, + 0xf5, 0x0, 0xbf, 0xb2, 0x0, 0x0, 0x9f, 0x50, + 0x0, 0xaf, 0xfd, 0xbc, 0xff, 0xd2, 0x0, 0x0, + 0x4a, 0xef, 0xeb, 0x60, 0x0, + + /* U+0048 "H" */ + 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, + 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, + 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, + 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xea, + 0xaa, 0xaa, 0xaa, 0xfb, 0x1f, 0xff, 0xff, 0xff, + 0xff, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, + 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, + 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, + 0x1, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, + 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, + + /* U+0049 "I" */ + 0x1f, 0xb1, 0xfb, 0x1f, 0xb1, 0xfb, 0x1f, 0xb1, + 0xfb, 0x1f, 0xb1, 0xfb, 0x1f, 0xb1, 0xfb, 0x1f, + 0xb1, 0xfb, 0x1f, 0xb0, + + /* U+004A "J" */ + 0x0, 0xef, 0xff, 0xff, 0x70, 0x8, 0xaa, 0xab, + 0xf7, 0x0, 0x0, 0x0, 0x5f, 0x70, 0x0, 0x0, + 0x5, 0xf7, 0x0, 0x0, 0x0, 0x5f, 0x70, 0x0, + 0x0, 0x5, 0xf7, 0x0, 0x0, 0x0, 0x5f, 0x70, + 0x0, 0x0, 0x5, 0xf7, 0x0, 0x0, 0x0, 0x5f, + 0x70, 0x0, 0x0, 0x6, 0xf6, 0xa, 0x70, 0x0, + 0xcf, 0x30, 0xcf, 0xda, 0xdf, 0xc0, 0x0, 0x8d, + 0xfe, 0x90, 0x0, + + /* U+004B "K" */ + 0x1f, 0xb0, 0x0, 0x0, 0x1d, 0xe2, 0x1f, 0xb0, + 0x0, 0x1, 0xdf, 0x30, 0x1f, 0xb0, 0x0, 0xc, + 0xf4, 0x0, 0x1f, 0xb0, 0x0, 0xbf, 0x50, 0x0, + 0x1f, 0xb0, 0xb, 0xf7, 0x0, 0x0, 0x1f, 0xb0, + 0xaf, 0x80, 0x0, 0x0, 0x1f, 0xb9, 0xff, 0xb0, + 0x0, 0x0, 0x1f, 0xff, 0xbb, 0xf8, 0x0, 0x0, + 0x1f, 0xfb, 0x1, 0xdf, 0x50, 0x0, 0x1f, 0xd0, + 0x0, 0x2f, 0xf2, 0x0, 0x1f, 0xb0, 0x0, 0x4, + 0xfd, 0x10, 0x1f, 0xb0, 0x0, 0x0, 0x7f, 0xb0, + 0x1f, 0xb0, 0x0, 0x0, 0x9, 0xf8, + + /* U+004C "L" */ + 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, + 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, + 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, + 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, + 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, + 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, + 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x1f, + 0xea, 0xaa, 0xaa, 0xa5, 0x1f, 0xff, 0xff, 0xff, + 0xf8, + + /* U+004D "M" */ + 0x1f, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0x41, + 0xff, 0x30, 0x0, 0x0, 0x0, 0x1f, 0xf4, 0x1f, + 0xfc, 0x0, 0x0, 0x0, 0x9, 0xff, 0x41, 0xff, + 0xf5, 0x0, 0x0, 0x2, 0xfe, 0xf4, 0x1f, 0xad, + 0xe0, 0x0, 0x0, 0xbe, 0x8f, 0x41, 0xfa, 0x4f, + 0x80, 0x0, 0x4f, 0x67, 0xf4, 0x1f, 0xa0, 0xaf, + 0x20, 0xd, 0xd0, 0x7f, 0x41, 0xfa, 0x2, 0xfa, + 0x7, 0xf4, 0x7, 0xf4, 0x1f, 0xa0, 0x8, 0xf5, + 0xea, 0x0, 0x7f, 0x41, 0xfa, 0x0, 0xe, 0xff, + 0x20, 0x6, 0xf4, 0x1f, 0xa0, 0x0, 0x5f, 0x80, + 0x0, 0x6f, 0x41, 0xfa, 0x0, 0x0, 0x60, 0x0, + 0x6, 0xf4, 0x1f, 0xa0, 0x0, 0x0, 0x0, 0x0, + 0x6f, 0x40, + + /* U+004E "N" */ + 0x1f, 0xb0, 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xf8, + 0x0, 0x0, 0x1, 0xfb, 0x1f, 0xff, 0x50, 0x0, + 0x1, 0xfb, 0x1f, 0xdf, 0xf2, 0x0, 0x1, 0xfb, + 0x1f, 0xb6, 0xfd, 0x0, 0x1, 0xfb, 0x1f, 0xb0, + 0x9f, 0xa0, 0x1, 0xfb, 0x1f, 0xb0, 0xc, 0xf6, + 0x1, 0xfb, 0x1f, 0xb0, 0x1, 0xef, 0x31, 0xfb, + 0x1f, 0xb0, 0x0, 0x4f, 0xe2, 0xfb, 0x1f, 0xb0, + 0x0, 0x7, 0xfd, 0xfb, 0x1f, 0xb0, 0x0, 0x0, + 0xbf, 0xfb, 0x1f, 0xb0, 0x0, 0x0, 0x1d, 0xfb, + 0x1f, 0xb0, 0x0, 0x0, 0x2, 0xfb, + + /* U+004F "O" */ + 0x0, 0x0, 0x4a, 0xdf, 0xeb, 0x50, 0x0, 0x0, + 0x0, 0xaf, 0xfc, 0xbc, 0xff, 0xc1, 0x0, 0x0, + 0xbf, 0xb2, 0x0, 0x1, 0xaf, 0xd0, 0x0, 0x6f, + 0xb0, 0x0, 0x0, 0x0, 0x9f, 0x80, 0xc, 0xf1, + 0x0, 0x0, 0x0, 0x0, 0xfe, 0x0, 0xfc, 0x0, + 0x0, 0x0, 0x0, 0xa, 0xf2, 0x1f, 0xa0, 0x0, + 0x0, 0x0, 0x0, 0x9f, 0x30, 0xfc, 0x0, 0x0, + 0x0, 0x0, 0xa, 0xf2, 0xc, 0xf1, 0x0, 0x0, + 0x0, 0x0, 0xfe, 0x0, 0x6f, 0xb0, 0x0, 0x0, + 0x0, 0x9f, 0x80, 0x0, 0xbf, 0xb2, 0x0, 0x1, + 0xaf, 0xd0, 0x0, 0x0, 0xaf, 0xfc, 0xbc, 0xff, + 0xc1, 0x0, 0x0, 0x0, 0x4a, 0xef, 0xeb, 0x50, + 0x0, 0x0, + + /* U+0050 "P" */ + 0x1f, 0xff, 0xff, 0xfc, 0x70, 0x0, 0x1f, 0xea, + 0xaa, 0xbe, 0xfd, 0x10, 0x1f, 0xb0, 0x0, 0x0, + 0x9f, 0x90, 0x1f, 0xb0, 0x0, 0x0, 0xe, 0xf0, + 0x1f, 0xb0, 0x0, 0x0, 0xc, 0xf0, 0x1f, 0xb0, + 0x0, 0x0, 0xe, 0xf0, 0x1f, 0xb0, 0x0, 0x0, + 0x9f, 0x90, 0x1f, 0xea, 0xaa, 0xbe, 0xfd, 0x10, + 0x1f, 0xff, 0xff, 0xfc, 0x70, 0x0, 0x1f, 0xb0, + 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, + 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x0, + 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x0, + + /* U+0051 "Q" */ + 0x0, 0x0, 0x4a, 0xdf, 0xeb, 0x50, 0x0, 0x0, + 0x0, 0xaf, 0xfc, 0xbc, 0xff, 0xc1, 0x0, 0x0, + 0xbf, 0xb2, 0x0, 0x1, 0xaf, 0xd0, 0x0, 0x6f, + 0xb0, 0x0, 0x0, 0x0, 0x9f, 0x80, 0xc, 0xf1, + 0x0, 0x0, 0x0, 0x0, 0xfe, 0x0, 0xfc, 0x0, + 0x0, 0x0, 0x0, 0xa, 0xf1, 0x1f, 0xa0, 0x0, + 0x0, 0x0, 0x0, 0x9f, 0x30, 0xfc, 0x0, 0x0, + 0x0, 0x0, 0xa, 0xf2, 0xd, 0xf1, 0x0, 0x0, + 0x0, 0x0, 0xfe, 0x0, 0x7f, 0xa0, 0x0, 0x0, + 0x0, 0x8f, 0x80, 0x0, 0xcf, 0xa1, 0x0, 0x0, + 0x9f, 0xd0, 0x0, 0x1, 0xcf, 0xfb, 0xab, 0xff, + 0xd1, 0x0, 0x0, 0x0, 0x6c, 0xef, 0xfd, 0x60, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x5f, 0xe6, 0x34, + 0xa7, 0x0, 0x0, 0x0, 0x0, 0x3c, 0xff, 0xfe, + 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, 0x43, 0x0, + + /* U+0052 "R" */ + 0x1f, 0xff, 0xff, 0xfc, 0x70, 0x0, 0x1f, 0xea, + 0xaa, 0xbe, 0xfd, 0x10, 0x1f, 0xb0, 0x0, 0x0, + 0x9f, 0x90, 0x1f, 0xb0, 0x0, 0x0, 0xe, 0xf0, + 0x1f, 0xb0, 0x0, 0x0, 0xc, 0xf0, 0x1f, 0xb0, + 0x0, 0x0, 0xe, 0xe0, 0x1f, 0xb0, 0x0, 0x0, + 0x9f, 0x90, 0x1f, 0xd9, 0x99, 0xae, 0xfd, 0x10, + 0x1f, 0xff, 0xff, 0xff, 0xa0, 0x0, 0x1f, 0xb0, + 0x0, 0x1f, 0xd0, 0x0, 0x1f, 0xb0, 0x0, 0x6, + 0xf9, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0xbf, 0x40, + 0x1f, 0xb0, 0x0, 0x0, 0x1e, 0xe0, + + /* U+0053 "S" */ + 0x0, 0x29, 0xdf, 0xfd, 0x81, 0x0, 0x3f, 0xfc, + 0x9a, 0xdf, 0xc0, 0xb, 0xf4, 0x0, 0x0, 0x23, + 0x0, 0xed, 0x0, 0x0, 0x0, 0x0, 0xc, 0xf3, + 0x0, 0x0, 0x0, 0x0, 0x5f, 0xfa, 0x61, 0x0, + 0x0, 0x0, 0x3b, 0xff, 0xfd, 0x70, 0x0, 0x0, + 0x0, 0x48, 0xef, 0xb0, 0x0, 0x0, 0x0, 0x0, + 0xbf, 0x40, 0x0, 0x0, 0x0, 0x6, 0xf6, 0xb, + 0x50, 0x0, 0x0, 0xcf, 0x31, 0xdf, 0xeb, 0x9a, + 0xef, 0x90, 0x0, 0x6b, 0xef, 0xeb, 0x50, 0x0, + + /* U+0054 "T" */ + 0xef, 0xff, 0xff, 0xff, 0xff, 0x89, 0xaa, 0xad, + 0xfb, 0xaa, 0xa5, 0x0, 0x0, 0x9f, 0x20, 0x0, + 0x0, 0x0, 0x9, 0xf2, 0x0, 0x0, 0x0, 0x0, + 0x9f, 0x20, 0x0, 0x0, 0x0, 0x9, 0xf2, 0x0, + 0x0, 0x0, 0x0, 0x9f, 0x20, 0x0, 0x0, 0x0, + 0x9, 0xf2, 0x0, 0x0, 0x0, 0x0, 0x9f, 0x20, + 0x0, 0x0, 0x0, 0x9, 0xf2, 0x0, 0x0, 0x0, + 0x0, 0x9f, 0x20, 0x0, 0x0, 0x0, 0x9, 0xf2, + 0x0, 0x0, 0x0, 0x0, 0x9f, 0x20, 0x0, 0x0, + + /* U+0055 "U" */ + 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, + 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, + 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf7, + 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, + 0x0, 0x0, 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, + 0x5, 0xf7, 0x3f, 0x90, 0x0, 0x0, 0x5, 0xf6, + 0x2f, 0xb0, 0x0, 0x0, 0x7, 0xf5, 0xe, 0xf0, + 0x0, 0x0, 0xb, 0xf2, 0x8, 0xfa, 0x0, 0x0, + 0x7f, 0xb0, 0x0, 0xcf, 0xfb, 0xbe, 0xfe, 0x20, + 0x0, 0x7, 0xcf, 0xfd, 0x81, 0x0, + + /* U+0056 "V" */ + 0xc, 0xf2, 0x0, 0x0, 0x0, 0x2, 0xf9, 0x6, + 0xf8, 0x0, 0x0, 0x0, 0x9, 0xf3, 0x0, 0xef, + 0x0, 0x0, 0x0, 0x1f, 0xc0, 0x0, 0x8f, 0x60, + 0x0, 0x0, 0x7f, 0x50, 0x0, 0x1f, 0xd0, 0x0, + 0x0, 0xee, 0x0, 0x0, 0xa, 0xf4, 0x0, 0x5, + 0xf7, 0x0, 0x0, 0x3, 0xfb, 0x0, 0xc, 0xf1, + 0x0, 0x0, 0x0, 0xdf, 0x20, 0x2f, 0xa0, 0x0, + 0x0, 0x0, 0x6f, 0x80, 0x9f, 0x30, 0x0, 0x0, + 0x0, 0xe, 0xe1, 0xfc, 0x0, 0x0, 0x0, 0x0, + 0x8, 0xfc, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x1, + 0xff, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xaf, + 0x80, 0x0, 0x0, + + /* U+0057 "W" */ + 0x4f, 0x90, 0x0, 0x0, 0xc, 0xf3, 0x0, 0x0, + 0x2, 0xf8, 0xe, 0xe0, 0x0, 0x0, 0x2f, 0xf8, + 0x0, 0x0, 0x8, 0xf3, 0x9, 0xf3, 0x0, 0x0, + 0x7f, 0xfd, 0x0, 0x0, 0xd, 0xe0, 0x4, 0xf8, + 0x0, 0x0, 0xcd, 0x8f, 0x20, 0x0, 0x2f, 0x80, + 0x0, 0xfe, 0x0, 0x2, 0xf8, 0x3f, 0x80, 0x0, + 0x7f, 0x30, 0x0, 0xaf, 0x30, 0x7, 0xf3, 0xe, + 0xd0, 0x0, 0xde, 0x0, 0x0, 0x5f, 0x80, 0xc, + 0xd0, 0x8, 0xf2, 0x2, 0xf9, 0x0, 0x0, 0xf, + 0xd0, 0x2f, 0x80, 0x3, 0xf7, 0x7, 0xf4, 0x0, + 0x0, 0xa, 0xf2, 0x7f, 0x30, 0x0, 0xed, 0xc, + 0xe0, 0x0, 0x0, 0x5, 0xf7, 0xde, 0x0, 0x0, + 0x9f, 0x4f, 0x90, 0x0, 0x0, 0x0, 0xfe, 0xf8, + 0x0, 0x0, 0x3f, 0xdf, 0x40, 0x0, 0x0, 0x0, + 0xbf, 0xf3, 0x0, 0x0, 0xe, 0xff, 0x0, 0x0, + 0x0, 0x0, 0x6f, 0xe0, 0x0, 0x0, 0x9, 0xfa, + 0x0, 0x0, + + /* U+0058 "X" */ + 0x2f, 0xd0, 0x0, 0x0, 0xb, 0xf3, 0x6, 0xfa, + 0x0, 0x0, 0x7f, 0x70, 0x0, 0xbf, 0x50, 0x2, + 0xfc, 0x0, 0x0, 0x1e, 0xe1, 0xd, 0xf2, 0x0, + 0x0, 0x5, 0xfb, 0x8f, 0x50, 0x0, 0x0, 0x0, + 0x9f, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xf5, + 0x0, 0x0, 0x0, 0x0, 0xdf, 0xfe, 0x10, 0x0, + 0x0, 0x9, 0xf6, 0x5f, 0xa0, 0x0, 0x0, 0x4f, + 0xb0, 0xa, 0xf6, 0x0, 0x1, 0xee, 0x10, 0x1, + 0xef, 0x20, 0xb, 0xf5, 0x0, 0x0, 0x4f, 0xc0, + 0x6f, 0xa0, 0x0, 0x0, 0x8, 0xf8, + + /* U+0059 "Y" */ + 0xc, 0xf2, 0x0, 0x0, 0x0, 0x5f, 0x60, 0x3f, + 0xb0, 0x0, 0x0, 0xe, 0xd0, 0x0, 0x9f, 0x50, + 0x0, 0x8, 0xf3, 0x0, 0x1, 0xee, 0x0, 0x2, + 0xfa, 0x0, 0x0, 0x6, 0xf8, 0x0, 0xbf, 0x10, + 0x0, 0x0, 0xc, 0xf1, 0x4f, 0x70, 0x0, 0x0, + 0x0, 0x3f, 0xbd, 0xd0, 0x0, 0x0, 0x0, 0x0, + 0xaf, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x2, 0xfc, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xb0, 0x0, + 0x0, 0x0, 0x0, 0x1, 0xfb, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x1f, 0xb0, 0x0, 0x0, 0x0, 0x0, + 0x1, 0xfb, 0x0, 0x0, 0x0, + + /* U+005A "Z" */ + 0x1f, 0xff, 0xff, 0xff, 0xff, 0xf1, 0xa, 0xaa, + 0xaa, 0xaa, 0xcf, 0xd0, 0x0, 0x0, 0x0, 0x1, + 0xef, 0x20, 0x0, 0x0, 0x0, 0xc, 0xf5, 0x0, + 0x0, 0x0, 0x0, 0x9f, 0x80, 0x0, 0x0, 0x0, + 0x5, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xe1, + 0x0, 0x0, 0x0, 0x0, 0xdf, 0x30, 0x0, 0x0, + 0x0, 0xa, 0xf6, 0x0, 0x0, 0x0, 0x0, 0x7f, + 0xa0, 0x0, 0x0, 0x0, 0x4, 0xfd, 0x0, 0x0, + 0x0, 0x0, 0x1e, 0xfb, 0xaa, 0xaa, 0xaa, 0xa2, + 0x3f, 0xff, 0xff, 0xff, 0xff, 0xf4, + + /* U+0061 "a" */ + 0x1, 0x7c, 0xff, 0xd6, 0x0, 0x9, 0xfc, 0x99, + 0xef, 0x80, 0x1, 0x30, 0x0, 0xd, 0xf0, 0x0, + 0x0, 0x0, 0x9, 0xf2, 0x1, 0x9e, 0xff, 0xff, + 0xf3, 0xa, 0xf8, 0x43, 0x3a, 0xf3, 0xf, 0xb0, + 0x0, 0x8, 0xf3, 0xf, 0xb0, 0x0, 0xe, 0xf3, + 0x9, 0xf9, 0x46, 0xdf, 0xf3, 0x0, 0x8d, 0xfe, + 0x87, 0xf3, + + /* U+0062 "b" */ + 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5, 0xf5, 0x0, + 0x0, 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, + 0x5, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x5f, 0x56, + 0xdf, 0xea, 0x20, 0x5, 0xfd, 0xfc, 0x9b, 0xff, + 0x30, 0x5f, 0xf5, 0x0, 0x4, 0xfe, 0x5, 0xfa, + 0x0, 0x0, 0x8, 0xf4, 0x5f, 0x60, 0x0, 0x0, + 0x4f, 0x75, 0xf6, 0x0, 0x0, 0x4, 0xf7, 0x5f, + 0xa0, 0x0, 0x0, 0x8f, 0x45, 0xff, 0x50, 0x0, + 0x4f, 0xe0, 0x5f, 0xcf, 0xc9, 0xbf, 0xf3, 0x5, + 0xf4, 0x6d, 0xfe, 0xa2, 0x0, + + /* U+0063 "c" */ + 0x0, 0x7, 0xdf, 0xeb, 0x30, 0x0, 0xcf, 0xd9, + 0xaf, 0xf4, 0x9, 0xf7, 0x0, 0x2, 0xc3, 0xf, + 0xd0, 0x0, 0x0, 0x0, 0x3f, 0x80, 0x0, 0x0, + 0x0, 0x3f, 0x80, 0x0, 0x0, 0x0, 0xf, 0xc0, + 0x0, 0x0, 0x0, 0x9, 0xf7, 0x0, 0x2, 0xc3, + 0x0, 0xcf, 0xd9, 0xaf, 0xf3, 0x0, 0x7, 0xdf, + 0xeb, 0x30, + + /* U+0064 "d" */ + 0x0, 0x0, 0x0, 0x0, 0x1f, 0xa0, 0x0, 0x0, + 0x0, 0x1, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x1f, + 0xa0, 0x0, 0x0, 0x0, 0x1, 0xfa, 0x0, 0x8, + 0xdf, 0xe8, 0x2f, 0xa0, 0x1d, 0xfd, 0x9b, 0xfd, + 0xfa, 0xa, 0xf8, 0x0, 0x2, 0xef, 0xa0, 0xfd, + 0x0, 0x0, 0x6, 0xfa, 0x3f, 0x80, 0x0, 0x0, + 0x2f, 0xa3, 0xf8, 0x0, 0x0, 0x2, 0xfa, 0xf, + 0xc0, 0x0, 0x0, 0x5f, 0xa0, 0xaf, 0x60, 0x0, + 0x1e, 0xfa, 0x1, 0xdf, 0xb7, 0x9e, 0xdf, 0xa0, + 0x0, 0x8d, 0xfe, 0x91, 0xfa, + + /* U+0065 "e" */ + 0x0, 0x8, 0xdf, 0xe9, 0x10, 0x0, 0x1d, 0xfb, + 0x8a, 0xfe, 0x20, 0xa, 0xf3, 0x0, 0x3, 0xfb, + 0x0, 0xfa, 0x0, 0x0, 0x9, 0xf1, 0x3f, 0xff, + 0xff, 0xff, 0xff, 0x33, 0xfa, 0x33, 0x33, 0x33, + 0x30, 0xf, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x9f, + 0x90, 0x0, 0x9, 0x10, 0x0, 0xdf, 0xda, 0xae, + 0xf6, 0x0, 0x0, 0x7d, 0xff, 0xc5, 0x0, + + /* U+0066 "f" */ + 0x0, 0x1a, 0xee, 0x90, 0xa, 0xf9, 0x88, 0x0, + 0xfb, 0x0, 0x0, 0x1f, 0x90, 0x0, 0xbf, 0xff, + 0xff, 0x55, 0x8f, 0xc7, 0x72, 0x1, 0xfa, 0x0, + 0x0, 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, + 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, 0x1f, + 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, 0x1f, 0xa0, + 0x0, + + /* U+0067 "g" */ + 0x0, 0x8, 0xdf, 0xe9, 0x1e, 0xc0, 0x1d, 0xfd, + 0x9b, 0xfe, 0xec, 0xa, 0xf8, 0x0, 0x1, 0xdf, + 0xc0, 0xfd, 0x0, 0x0, 0x4, 0xfc, 0x3f, 0x90, + 0x0, 0x0, 0xf, 0xc3, 0xf8, 0x0, 0x0, 0x0, + 0xfc, 0xf, 0xd0, 0x0, 0x0, 0x4f, 0xc0, 0xaf, + 0x80, 0x0, 0x1d, 0xfc, 0x1, 0xdf, 0xd9, 0xaf, + 0xdf, 0xc0, 0x0, 0x8d, 0xfe, 0x91, 0xfb, 0x0, + 0x0, 0x0, 0x0, 0x2f, 0x90, 0x27, 0x0, 0x0, + 0xb, 0xf4, 0x7, 0xff, 0xb9, 0xae, 0xfa, 0x0, + 0x4, 0xae, 0xff, 0xc6, 0x0, + + /* U+0068 "h" */ + 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5f, 0x50, 0x0, + 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5f, + 0x50, 0x0, 0x0, 0x0, 0x5f, 0x56, 0xdf, 0xea, + 0x10, 0x5f, 0xef, 0xca, 0xdf, 0xd0, 0x5f, 0xf4, + 0x0, 0xa, 0xf6, 0x5f, 0x90, 0x0, 0x2, 0xf9, + 0x5f, 0x60, 0x0, 0x0, 0xfa, 0x5f, 0x50, 0x0, + 0x0, 0xfb, 0x5f, 0x50, 0x0, 0x0, 0xfb, 0x5f, + 0x50, 0x0, 0x0, 0xfb, 0x5f, 0x50, 0x0, 0x0, + 0xfb, 0x5f, 0x50, 0x0, 0x0, 0xfb, + + /* U+0069 "i" */ + 0x6f, 0x69, 0xf9, 0x4, 0x0, 0x0, 0x5f, 0x55, + 0xf5, 0x5f, 0x55, 0xf5, 0x5f, 0x55, 0xf5, 0x5f, + 0x55, 0xf5, 0x5f, 0x55, 0xf5, + + /* U+006A "j" */ + 0x0, 0x4, 0xf7, 0x0, 0x7, 0xfa, 0x0, 0x0, + 0x40, 0x0, 0x0, 0x0, 0x0, 0x4, 0xf7, 0x0, + 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x4, 0xf7, + 0x0, 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x4, + 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, + 0x4, 0xf7, 0x0, 0x4, 0xf7, 0x0, 0x6, 0xf5, + 0x4b, 0x9f, 0xe1, 0x5e, 0xfc, 0x30, + + /* U+006B "k" */ + 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5, 0xf5, 0x0, + 0x0, 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, + 0x5, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x5f, 0x50, + 0x0, 0x1d, 0xf3, 0x5, 0xf5, 0x0, 0x2d, 0xf3, + 0x0, 0x5f, 0x50, 0x2e, 0xf4, 0x0, 0x5, 0xf5, + 0x2e, 0xf4, 0x0, 0x0, 0x5f, 0x9e, 0xfe, 0x0, + 0x0, 0x5, 0xff, 0xfa, 0xfa, 0x0, 0x0, 0x5f, + 0xe3, 0xc, 0xf6, 0x0, 0x5, 0xf6, 0x0, 0x1e, + 0xf3, 0x0, 0x5f, 0x50, 0x0, 0x3f, 0xd0, 0x5, + 0xf5, 0x0, 0x0, 0x7f, 0xa0, + + /* U+006C "l" */ + 0x5f, 0x55, 0xf5, 0x5f, 0x55, 0xf5, 0x5f, 0x55, + 0xf5, 0x5f, 0x55, 0xf5, 0x5f, 0x55, 0xf5, 0x5f, + 0x55, 0xf5, 0x5f, 0x55, 0xf5, + + /* U+006D "m" */ + 0x5f, 0x58, 0xdf, 0xe8, 0x0, 0x8d, 0xfe, 0x80, + 0x5, 0xfe, 0xfa, 0x9d, 0xfb, 0xdf, 0xa9, 0xdf, + 0xb0, 0x5f, 0xf2, 0x0, 0xd, 0xff, 0x30, 0x0, + 0xcf, 0x35, 0xf9, 0x0, 0x0, 0x7f, 0xa0, 0x0, + 0x6, 0xf6, 0x5f, 0x60, 0x0, 0x5, 0xf7, 0x0, + 0x0, 0x4f, 0x75, 0xf5, 0x0, 0x0, 0x5f, 0x60, + 0x0, 0x4, 0xf7, 0x5f, 0x50, 0x0, 0x5, 0xf6, + 0x0, 0x0, 0x4f, 0x75, 0xf5, 0x0, 0x0, 0x5f, + 0x60, 0x0, 0x4, 0xf7, 0x5f, 0x50, 0x0, 0x5, + 0xf6, 0x0, 0x0, 0x4f, 0x75, 0xf5, 0x0, 0x0, + 0x5f, 0x60, 0x0, 0x4, 0xf7, + + /* U+006E "n" */ + 0x5f, 0x57, 0xdf, 0xea, 0x10, 0x5f, 0xef, 0xa8, + 0xcf, 0xd0, 0x5f, 0xf3, 0x0, 0x9, 0xf6, 0x5f, + 0x90, 0x0, 0x2, 0xf9, 0x5f, 0x60, 0x0, 0x0, + 0xfa, 0x5f, 0x50, 0x0, 0x0, 0xfb, 0x5f, 0x50, + 0x0, 0x0, 0xfb, 0x5f, 0x50, 0x0, 0x0, 0xfb, + 0x5f, 0x50, 0x0, 0x0, 0xfb, 0x5f, 0x50, 0x0, + 0x0, 0xfb, + + /* U+006F "o" */ + 0x0, 0x7, 0xdf, 0xea, 0x30, 0x0, 0xd, 0xfd, + 0x9a, 0xff, 0x50, 0x9, 0xf7, 0x0, 0x2, 0xef, + 0x10, 0xfd, 0x0, 0x0, 0x6, 0xf7, 0x3f, 0x80, + 0x0, 0x0, 0x2f, 0x93, 0xf8, 0x0, 0x0, 0x2, + 0xf9, 0xf, 0xd0, 0x0, 0x0, 0x6f, 0x60, 0x9f, + 0x80, 0x0, 0x2e, 0xf1, 0x0, 0xcf, 0xd9, 0xaf, + 0xf4, 0x0, 0x0, 0x7d, 0xfe, 0xa3, 0x0, + + /* U+0070 "p" */ + 0x5f, 0x46, 0xdf, 0xea, 0x20, 0x5, 0xfd, 0xfa, + 0x8a, 0xff, 0x30, 0x5f, 0xf4, 0x0, 0x3, 0xfe, + 0x5, 0xfa, 0x0, 0x0, 0x8, 0xf4, 0x5f, 0x60, + 0x0, 0x0, 0x4f, 0x75, 0xf6, 0x0, 0x0, 0x4, + 0xf7, 0x5f, 0xa0, 0x0, 0x0, 0x9f, 0x45, 0xff, + 0x50, 0x0, 0x4f, 0xe0, 0x5f, 0xdf, 0xc9, 0xbf, + 0xf3, 0x5, 0xf5, 0x6d, 0xfe, 0xa2, 0x0, 0x5f, + 0x50, 0x0, 0x0, 0x0, 0x5, 0xf5, 0x0, 0x0, + 0x0, 0x0, 0x5f, 0x50, 0x0, 0x0, 0x0, 0x5, + 0xf5, 0x0, 0x0, 0x0, 0x0, + + /* U+0071 "q" */ + 0x0, 0x8, 0xdf, 0xe8, 0x1f, 0xa0, 0x1d, 0xfd, + 0x9b, 0xfc, 0xfa, 0xa, 0xf7, 0x0, 0x2, 0xef, + 0xa0, 0xfd, 0x0, 0x0, 0x6, 0xfa, 0x3f, 0x80, + 0x0, 0x0, 0x2f, 0xa3, 0xf8, 0x0, 0x0, 0x2, + 0xfa, 0xf, 0xd0, 0x0, 0x0, 0x6f, 0xa0, 0xaf, + 0x80, 0x0, 0x2e, 0xfa, 0x1, 0xdf, 0xd9, 0xaf, + 0xdf, 0xa0, 0x0, 0x8d, 0xfe, 0x82, 0xfa, 0x0, + 0x0, 0x0, 0x0, 0x1f, 0xa0, 0x0, 0x0, 0x0, + 0x1, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xa0, + 0x0, 0x0, 0x0, 0x1, 0xfa, + + /* U+0072 "r" */ + 0x5f, 0x46, 0xdb, 0x5f, 0xcf, 0xd9, 0x5f, 0xf5, + 0x0, 0x5f, 0xa0, 0x0, 0x5f, 0x70, 0x0, 0x5f, + 0x50, 0x0, 0x5f, 0x50, 0x0, 0x5f, 0x50, 0x0, + 0x5f, 0x50, 0x0, 0x5f, 0x50, 0x0, + + /* U+0073 "s" */ + 0x1, 0x8d, 0xfe, 0xc7, 0x0, 0xcf, 0xb8, 0xad, + 0xd0, 0x3f, 0x90, 0x0, 0x1, 0x2, 0xfb, 0x0, + 0x0, 0x0, 0xb, 0xff, 0xb8, 0x40, 0x0, 0x5, + 0x9c, 0xff, 0xc0, 0x0, 0x0, 0x0, 0x9f, 0x60, + 0x50, 0x0, 0x5, 0xf7, 0x5f, 0xea, 0x9a, 0xfe, + 0x10, 0x6c, 0xef, 0xd9, 0x20, + + /* U+0074 "t" */ + 0x1, 0xfa, 0x0, 0x0, 0x1f, 0xa0, 0x0, 0xbf, + 0xff, 0xff, 0x55, 0x8f, 0xc7, 0x72, 0x1, 0xfa, + 0x0, 0x0, 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, + 0x0, 0x1f, 0xa0, 0x0, 0x1, 0xfa, 0x0, 0x0, + 0xf, 0xc0, 0x0, 0x0, 0xbf, 0xa9, 0x90, 0x1, + 0xbe, 0xe9, + + /* U+0075 "u" */ + 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, + 0x3, 0xf8, 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, + 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, 0x3, + 0xf8, 0x7f, 0x40, 0x0, 0x4, 0xf8, 0x6f, 0x60, + 0x0, 0x6, 0xf8, 0x2f, 0xc0, 0x0, 0x1e, 0xf8, + 0xa, 0xfd, 0x89, 0xee, 0xf8, 0x0, 0x8d, 0xfe, + 0x92, 0xf8, + + /* U+0076 "v" */ + 0xd, 0xe0, 0x0, 0x0, 0xd, 0xd0, 0x6, 0xf6, + 0x0, 0x0, 0x3f, 0x70, 0x0, 0xfc, 0x0, 0x0, + 0xaf, 0x10, 0x0, 0x9f, 0x30, 0x1, 0xf9, 0x0, + 0x0, 0x2f, 0x90, 0x7, 0xf3, 0x0, 0x0, 0xb, + 0xf0, 0xe, 0xc0, 0x0, 0x0, 0x5, 0xf6, 0x5f, + 0x50, 0x0, 0x0, 0x0, 0xed, 0xbe, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xf8, 0x0, 0x0, 0x0, 0x0, + 0x1f, 0xf1, 0x0, 0x0, + + /* U+0077 "w" */ + 0xbe, 0x0, 0x0, 0xc, 0xf1, 0x0, 0x0, 0xae, + 0x5, 0xf4, 0x0, 0x2, 0xff, 0x60, 0x0, 0xf, + 0x80, 0xf, 0x90, 0x0, 0x8f, 0xeb, 0x0, 0x5, + 0xf2, 0x0, 0xae, 0x0, 0xd, 0xb8, 0xf1, 0x0, + 0xbd, 0x0, 0x4, 0xf4, 0x3, 0xf5, 0x2f, 0x70, + 0x1f, 0x70, 0x0, 0xe, 0xa0, 0x9e, 0x0, 0xcc, + 0x6, 0xf1, 0x0, 0x0, 0x9f, 0x1e, 0x90, 0x6, + 0xf2, 0xcc, 0x0, 0x0, 0x3, 0xfa, 0xf3, 0x0, + 0x1f, 0xaf, 0x60, 0x0, 0x0, 0xd, 0xfd, 0x0, + 0x0, 0xbf, 0xf1, 0x0, 0x0, 0x0, 0x8f, 0x70, + 0x0, 0x5, 0xfb, 0x0, 0x0, + + /* U+0078 "x" */ + 0x3f, 0xb0, 0x0, 0xc, 0xf2, 0x7, 0xf7, 0x0, + 0x7f, 0x60, 0x0, 0xbf, 0x33, 0xfa, 0x0, 0x0, + 0x1e, 0xde, 0xd0, 0x0, 0x0, 0x4, 0xff, 0x30, + 0x0, 0x0, 0x6, 0xff, 0x50, 0x0, 0x0, 0x3f, + 0xbc, 0xf2, 0x0, 0x0, 0xde, 0x12, 0xfc, 0x0, + 0xa, 0xf4, 0x0, 0x5f, 0x90, 0x6f, 0x80, 0x0, + 0xa, 0xf5, + + /* U+0079 "y" */ + 0xd, 0xe0, 0x0, 0x0, 0xd, 0xd0, 0x6, 0xf6, + 0x0, 0x0, 0x3f, 0x70, 0x0, 0xfc, 0x0, 0x0, + 0x9f, 0x10, 0x0, 0x9f, 0x30, 0x1, 0xfa, 0x0, + 0x0, 0x2f, 0x90, 0x6, 0xf3, 0x0, 0x0, 0xc, + 0xf0, 0xd, 0xc0, 0x0, 0x0, 0x5, 0xf6, 0x3f, + 0x60, 0x0, 0x0, 0x0, 0xed, 0xae, 0x0, 0x0, + 0x0, 0x0, 0x8f, 0xf8, 0x0, 0x0, 0x0, 0x0, + 0x1f, 0xf2, 0x0, 0x0, 0x0, 0x0, 0xf, 0xb0, + 0x0, 0x0, 0x1, 0x0, 0x7f, 0x40, 0x0, 0x0, + 0x1f, 0xaa, 0xfb, 0x0, 0x0, 0x0, 0x19, 0xee, + 0xa1, 0x0, 0x0, 0x0, + + /* U+007A "z" */ + 0x2f, 0xff, 0xff, 0xff, 0x91, 0x77, 0x77, 0x7e, + 0xf4, 0x0, 0x0, 0x6, 0xf8, 0x0, 0x0, 0x3, + 0xfc, 0x0, 0x0, 0x1, 0xee, 0x10, 0x0, 0x0, + 0xbf, 0x40, 0x0, 0x0, 0x8f, 0x70, 0x0, 0x0, + 0x4f, 0xb0, 0x0, 0x0, 0x1e, 0xf8, 0x77, 0x77, + 0x54, 0xff, 0xff, 0xff, 0xfb, + + /* U+00B0 "°" */ + 0x1, 0xaf, 0xd5, 0x0, 0xb8, 0x3, 0xe4, 0x1e, + 0x0, 0x6, 0xa2, 0xe0, 0x0, 0x6a, 0xc, 0x70, + 0x1d, 0x50, 0x2c, 0xff, 0x70, 0x0, 0x0, 0x0, + 0x0, + + /* U+00E9 "é" */ + 0x0, 0x0, 0x0, 0xcf, 0x40, 0x0, 0x0, 0x0, + 0xce, 0x20, 0x0, 0x0, 0x0, 0x58, 0x10, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x8, + 0xdf, 0xe9, 0x10, 0x0, 0x1d, 0xfb, 0x8a, 0xfe, + 0x20, 0xa, 0xf3, 0x0, 0x3, 0xfb, 0x0, 0xfa, + 0x0, 0x0, 0x9, 0xf1, 0x3f, 0xff, 0xff, 0xff, + 0xff, 0x33, 0xfa, 0x33, 0x33, 0x33, 0x30, 0xf, + 0xd0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0x90, 0x0, + 0x9, 0x10, 0x0, 0xdf, 0xda, 0xae, 0xf6, 0x0, + 0x0, 0x7d, 0xff, 0xc5, 0x0, + + /* U+00FB "û" */ + 0x0, 0x4, 0xff, 0x50, 0x0, 0x0, 0x3f, 0x87, + 0xf5, 0x0, 0x0, 0x75, 0x0, 0x47, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x7f, 0x40, 0x0, 0x3, + 0xf8, 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, + 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, 0x3, 0xf8, + 0x7f, 0x40, 0x0, 0x3, 0xf8, 0x7f, 0x40, 0x0, + 0x4, 0xf8, 0x6f, 0x60, 0x0, 0x6, 0xf8, 0x2f, + 0xc0, 0x0, 0x1e, 0xf8, 0xa, 0xfd, 0x89, 0xee, + 0xf8, 0x0, 0x8d, 0xfe, 0x92, 0xf8, + + /* U+F015 "" */ + 0x0, 0x0, 0x0, 0x0, 0xb, 0xd3, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1d, 0xff, + 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x3e, 0xff, 0xff, 0xf6, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x4f, 0xff, 0xff, 0xff, 0xf8, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x6f, 0xff, 0xff, 0xff, + 0xff, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xfc, 0x10, 0x0, 0x0, + 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfd, + 0x20, 0x1, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xfe, 0x30, 0xcf, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x2c, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf2, 0x2, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x31, 0x0, 0xb, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0, 0x0, 0xbf, + 0xff, 0xff, 0x96, 0x67, 0xff, 0xff, 0xff, 0x0, + 0x0, 0xb, 0xff, 0xff, 0xf0, 0x0, 0x9, 0xff, + 0xff, 0xf1, 0x0, 0x0, 0xbf, 0xff, 0xfe, 0x0, + 0x0, 0x9f, 0xff, 0xff, 0x10, 0x0, 0xb, 0xff, + 0xff, 0xe0, 0x0, 0x9, 0xff, 0xff, 0xf1, 0x0, + 0x0, 0xbf, 0xff, 0xfe, 0x0, 0x0, 0x9f, 0xff, + 0xff, 0x0, 0x0, 0x5, 0xff, 0xff, 0x80, 0x0, + 0x3, 0xff, 0xff, 0xa0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + + /* U+F0C2 "" */ + 0x0, 0x0, 0x0, 0x16, 0x98, 0x60, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x5e, 0xff, + 0xff, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x5f, 0xff, 0xff, 0xff, 0xf5, 0x15, 0x30, + 0x0, 0x0, 0x0, 0x0, 0x1e, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xc1, 0x0, 0x0, 0x0, 0x6, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xb0, + 0x0, 0x0, 0x0, 0x9f, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0x0, 0x0, 0x0, 0x3d, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0, + 0x0, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x81, 0x0, 0x3f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe3, 0xb, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xd0, 0xef, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x4f, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xf7, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x65, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf1, 0x9, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf7, 0x0, 0x6, 0xdf, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xd5, 0x0, + 0x0, 0x0, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, + 0x11, 0x10, 0x0, 0x0 +}; + + +/*--------------------- + * GLYPH DESCRIPTION + *--------------------*/ + +static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { + {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, + {.bitmap_index = 0, .adv_w = 77, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 0, .adv_w = 60, .box_w = 2, .box_h = 6, .ofs_x = 1, .ofs_y = 7}, + {.bitmap_index = 6, .adv_w = 110, .box_w = 5, .box_h = 2, .ofs_x = 1, .ofs_y = 4}, + {.bitmap_index = 11, .adv_w = 65, .box_w = 4, .box_h = 3, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 17, .adv_w = 192, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 95, .adv_w = 107, .box_w = 5, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 128, .adv_w = 165, .box_w = 10, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 193, .adv_w = 165, .box_w = 10, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 258, .adv_w = 193, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 336, .adv_w = 165, .box_w = 10, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 401, .adv_w = 178, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 473, .adv_w = 172, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 545, .adv_w = 185, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 617, .adv_w = 178, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 689, .adv_w = 65, .box_w = 4, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 709, .adv_w = 211, .box_w = 15, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 807, .adv_w = 218, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 885, .adv_w = 208, .box_w = 13, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 970, .adv_w = 238, .box_w = 13, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1055, .adv_w = 193, .box_w = 11, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1127, .adv_w = 183, .box_w = 10, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1192, .adv_w = 222, .box_w = 13, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1277, .adv_w = 234, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1355, .adv_w = 89, .box_w = 3, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1375, .adv_w = 148, .box_w = 9, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 1434, .adv_w = 207, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1512, .adv_w = 171, .box_w = 10, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1577, .adv_w = 275, .box_w = 15, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1675, .adv_w = 234, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1753, .adv_w = 242, .box_w = 15, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1851, .adv_w = 208, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1929, .adv_w = 242, .box_w = 15, .box_h = 16, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 2049, .adv_w = 209, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 2127, .adv_w = 179, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2199, .adv_w = 169, .box_w = 11, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2271, .adv_w = 228, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 2349, .adv_w = 205, .box_w = 14, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 2440, .adv_w = 324, .box_w = 20, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2570, .adv_w = 194, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2648, .adv_w = 186, .box_w = 13, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 2733, .adv_w = 189, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2811, .adv_w = 172, .box_w = 10, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2861, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 2938, .adv_w = 164, .box_w = 10, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 2988, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3065, .adv_w = 176, .box_w = 11, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3120, .adv_w = 102, .box_w = 7, .box_h = 14, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3169, .adv_w = 199, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = -4}, + {.bitmap_index = 3246, .adv_w = 196, .box_w = 10, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3316, .adv_w = 80, .box_w = 3, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3337, .adv_w = 82, .box_w = 6, .box_h = 18, .ofs_x = -2, .ofs_y = -4}, + {.bitmap_index = 3391, .adv_w = 177, .box_w = 11, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3468, .adv_w = 80, .box_w = 3, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3489, .adv_w = 304, .box_w = 17, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3574, .adv_w = 196, .box_w = 10, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3624, .adv_w = 183, .box_w = 11, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3679, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 1, .ofs_y = -4}, + {.bitmap_index = 3756, .adv_w = 196, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = -4}, + {.bitmap_index = 3833, .adv_w = 118, .box_w = 6, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3863, .adv_w = 144, .box_w = 9, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3908, .adv_w = 119, .box_w = 7, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3950, .adv_w = 195, .box_w = 10, .box_h = 10, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 4000, .adv_w = 161, .box_w = 12, .box_h = 10, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 4060, .adv_w = 259, .box_w = 17, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 4145, .adv_w = 159, .box_w = 10, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 4195, .adv_w = 161, .box_w = 12, .box_h = 14, .ofs_x = -1, .ofs_y = -4}, + {.bitmap_index = 4279, .adv_w = 150, .box_w = 9, .box_h = 10, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 4324, .adv_w = 121, .box_w = 7, .box_h = 7, .ofs_x = 0, .ofs_y = 6}, + {.bitmap_index = 4349, .adv_w = 176, .box_w = 11, .box_h = 14, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 4426, .adv_w = 195, .box_w = 10, .box_h = 14, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 4496, .adv_w = 324, .box_w = 21, .box_h = 19, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 4696, .adv_w = 360, .box_w = 23, .box_h = 17, .ofs_x = 0, .ofs_y = -2} +}; + +/*--------------------- + * CHARACTER MAPPING + *--------------------*/ + +static const uint16_t unicode_list_0[] = { + 0x0, 0x7, 0xd, 0xe +}; + +static const uint16_t unicode_list_4[] = { + 0x0, 0x39, 0x4b, 0xef65, 0xf012 +}; + +/*Collect the unicode lists and glyph_id offsets*/ +static const lv_font_fmt_txt_cmap_t cmaps[] = +{ + { + .range_start = 32, .range_length = 15, .glyph_id_start = 1, + .unicode_list = unicode_list_0, .glyph_id_ofs_list = NULL, .list_length = 4, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY + }, + { + .range_start = 48, .range_length = 11, .glyph_id_start = 5, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 65, .range_length = 26, .glyph_id_start = 16, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 97, .range_length = 26, .glyph_id_start = 42, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 176, .range_length = 61459, .glyph_id_start = 68, + .unicode_list = unicode_list_4, .glyph_id_ofs_list = NULL, .list_length = 5, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY + } +}; + +/*----------------- + * KERNING + *----------------*/ + + +/*Map glyph_ids to kern left classes*/ +static const uint8_t kern_left_class_mapping[] = +{ + 0, 0, 1, 2, 3, 4, 0, 5, + 6, 7, 8, 9, 10, 11, 4, 12, + 13, 14, 15, 16, 17, 18, 19, 20, + 20, 21, 22, 23, 20, 20, 16, 24, + 16, 25, 26, 27, 21, 28, 28, 29, + 30, 31, 32, 33, 34, 35, 36, 37, + 38, 32, 38, 38, 39, 35, 32, 32, + 33, 33, 40, 41, 42, 43, 38, 44, + 44, 45, 44, 46, 47, 36, 38, 0, + 0 +}; + +/*Map glyph_ids to kern right classes*/ +static const uint8_t kern_right_class_mapping[] = +{ + 0, 0, 1, 2, 3, 4, 5, 6, + 7, 8, 9, 4, 10, 11, 12, 13, + 14, 15, 16, 15, 15, 15, 16, 15, + 15, 17, 15, 15, 15, 15, 16, 15, + 16, 15, 18, 19, 20, 21, 21, 22, + 23, 24, 25, 26, 27, 27, 27, 0, + 27, 26, 28, 29, 26, 26, 30, 30, + 27, 30, 27, 30, 31, 32, 33, 34, + 34, 35, 34, 36, 37, 27, 33, 0, + 0 +}; + +/*Kern values between classes*/ +static const int8_t kern_class_values[] = +{ + 13, 0, -16, 2, 14, 6, 5, -12, + 2, 14, 1, 12, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, 1, -2, + 2, -5, -4, -6, 2, 0, -3, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -16, -2, 0, -3, -4, 3, + 3, -3, 0, -4, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -18, 2, + 2, -3, 0, -1, -1, -3, 0, 0, + -2, 0, 0, 0, -2, 0, 0, -7, + 0, -6, 0, -7, -10, -10, -5, 0, + 0, 0, 0, -2, 0, 0, 3, 0, + 2, -3, 0, 1, 0, -2, 3, -1, + 0, 0, 0, -5, 0, -1, 0, 0, + 0, 1, 0, 0, 4, 0, -2, 0, + -3, 0, -5, 0, 0, 0, -3, 0, + 0, 0, 0, 0, -1, 1, -2, -2, + 0, -3, 0, 0, 0, 0, -1, -1, + 0, -3, -3, 0, 0, 0, 1, 0, + 0, 0, 0, -2, 0, -3, -3, -3, + 0, 0, 0, 0, 0, -2, 0, 0, + 0, 0, -2, -4, 0, -4, -9, 3, + 6, 0, -7, -1, -3, 0, -1, -14, + 3, -2, 2, 0, 0, 3, 1, -2, + -15, 0, -15, -2, -25, -2, 8, 0, + 4, 0, 0, 0, 0, 1, 0, -5, + -4, 0, -9, 0, 0, 0, 0, 0, + -1, -1, 0, -1, -4, 0, 0, 0, + 0, 0, 0, -3, 0, -3, 0, -2, + -3, -2, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -2, -2, 0, -3, + -2, 1, 3, 0, 0, 0, 0, 0, + 0, -2, 0, 0, 0, 2, 0, 0, + 0, 0, -3, 0, -3, -2, -3, 0, + 0, 0, 2, 0, -2, 0, 0, 0, + 0, -3, -4, 0, -5, 9, -14, -15, + -6, 3, 0, -2, -19, -5, 0, -5, + 0, -6, -18, 0, -5, -8, -2, 0, + 0, 1, -1, 2, -2, -11, 0, -14, + -7, -6, -7, -9, -3, -8, -1, -5, + -8, 2, 1, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, -1, + 0, 0, -1, 0, -3, 0, -5, -6, + -6, -1, 0, 0, 0, 0, -2, 0, + 0, 0, 0, 1, -2, 0, 0, 3, + 0, 0, 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -12, -5, 10, -2, + -12, 0, 3, -4, 0, -14, -1, -4, + 3, 4, 0, -3, 4, 0, -10, -4, + -11, -10, -12, 0, 0, 0, -1, 0, + 0, 0, -1, -1, -3, -8, -10, -1, + -27, 0, 0, 1, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -3, 0, -1, -3, -4, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, -1, + 4, -6, 3, -2, -1, -7, -3, 0, + -4, -3, -2, -5, 0, -4, 0, -1, + -2, -1, -2, -5, -3, 0, -2, 0, + -6, 0, 0, 0, -6, 0, -5, 0, + -5, -5, 3, -5, 2, -6, 0, -3, + -3, -3, 0, 0, 0, 0, 0, 0, + -3, 0, 0, -4, 0, -3, 0, -6, + -7, -9, -2, 0, 0, 0, 0, 23, + 0, 0, 1, 0, 0, -4, 0, 3, + 0, -6, 3, -4, 0, -2, -3, -9, + -2, -2, -2, -1, -2, 0, 0, -1, + 0, 0, 0, 0, -3, -2, -2, 0, + -2, 0, -2, 0, 0, 0, -2, -3, + -2, -3, -3, -3, 0, 12, 0, -3, + -4, 4, 0, 0, -14, -5, 3, -5, + 2, 0, -9, 0, -2, -4, -1, 1, + 0, 0, -5, 0, 0, -5, 0, -5, + -3, -4, -3, -3, 0, -5, 1, -5, + -5, 9, 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -2, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -2, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -4, 0, 0, 0, 0, -4, 0, + 0, -3, -3, 0, 0, 0, 0, 0, + -1, 0, 0, 0, 0, 0, -2, 0, + 0, 0, -10, 0, -6, 6, 1, -2, + -14, 0, 0, -6, -3, 0, -8, 0, + -7, 0, -4, -12, -3, -12, -11, -14, + 0, -4, 0, -7, -3, -1, -3, -5, + -8, -5, -11, -12, -7, -3, 0, -3, + 9, -6, -11, 0, 1, -9, 0, -14, + -2, -3, 6, 1, 0, -4, 0, -2, + -19, -3, -15, -3, -21, 0, 1, 0, + -2, 0, 0, 0, 0, -1, -2, -11, + -2, 0, -19, 0, -1, -8, 0, 0, + -1, -4, -9, -3, 0, -2, 0, 0, + -13, -3, 0, -10, 0, -9, -2, -5, + -7, -3, -5, -4, 0, -3, -5, -3, + -5, 0, 1, 0, -2, -10, 0, 6, + 0, -1, 0, 0, 0, 0, -2, -6, + 0, 0, 0, 0, 0, 0, 0, 0, + -3, 0, -3, 0, 0, -6, -3, 0, + -1, 0, 0, 0, 0, 0, 0, 1, + 0, 0, 0, 0, 4, -9, 5, 6, + 0, -3, 0, -2, 3, 0, -3, 0, + -3, -1, 0, 0, 0, 0, 0, -3, + 0, 0, -4, -4, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -3, -3, + 0, -4, 2, -10, -9, -6, 12, 5, + 3, -25, -2, 6, -3, 0, -3, -10, + 0, -3, -3, -3, 3, -4, -2, -9, + -2, 0, -8, 0, -16, -4, 8, -4, + -11, 1, -4, -10, -10, -3, 12, 0, + -7, -11, -7, 9, 0, 1, -21, -2, + 3, -5, -2, -7, -11, -4, -6, -4, + -4, -2, 0, 0, -7, -6, -3, -16, + 0, -16, -4, 0, -10, -17, -1, -9, + -5, -10, -8, 8, 0, -5, 0, -10, + 3, 0, 0, -15, 0, -3, -6, -5, + -2, -10, -7, -7, 0, -4, -9, -3, + -7, -5, -9, -3, -5, 0, -9, -3, + 0, -3, -6, -7, -8, -8, -11, -4, + -6, 0, -9, -11, -10, 10, -3, 1, + -27, -5, 6, -6, -5, -11, -12, -3, + -9, -3, -4, -2, -3, -6, -9, -1, + 0, -19, 0, -17, -7, 7, -11, -20, + -6, -10, -12, -14, -10, 6, 0, -3, + 6, -5, 6, 0, 0, -9, -1, 0, + -1, 0, 1, 0, 0, -2, 0, 0, + 0, 0, 0, -3, 0, 0, 1, 0, + -3, 0, 0, 0, 0, -2, -2, -3, + 0, 0, 0, 0, 0, 0, 0, -6, + -1, 0, 0, 0, -6, 0, -3, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 1, 0, 0, + 0, 0, 0, 0, -3, 0, 0, -5, + -4, 3, -3, 0, -8, -3, -7, 0, + 0, -8, 0, -3, 0, -3, 0, 0, + 0, 0, -23, -5, -12, -3, -10, 0, + -1, 0, 0, 0, 0, 0, 0, 0, + 0, -4, -5, -2, -5, 0, -3, 6, + -2, -7, -2, -5, -5, 0, -3, -1, + -2, 2, 0, 0, -1, 0, 0, -25, + -2, -4, 0, -6, 0, 0, -2, -2, + 0, 0, 0, 0, 2, 0, -2, -5, + -2, 5, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 4, 0, 0, 0, 0, 0, -6, + 3, 0, 0, -8, -3, -6, 0, 0, + -8, 0, -3, 0, 0, 0, 0, 0, + 0, -28, 0, -6, -11, -14, 0, -4, + 0, 0, 0, 0, 0, 0, 0, 0, + -3, -4, -1, -4, 0, -3, -3, 3, + 14, 5, 6, -8, 3, 12, 3, 8, + 6, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -3, 0, -2, 23, + 12, 23, 0, 0, 0, 3, 0, 0, + 11, 0, 0, 0, 0, -2, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -5, -24, -3, -2, -12, -14, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, -7, + 3, -3, 2, 5, 3, -9, 0, -1, + -2, 3, 0, 0, 0, 0, 0, 0, + -7, 0, -3, -2, -6, 0, -3, 0, + -6, -2, 0, -2, -5, 0, -3, -8, + -6, -3, 0, 0, 0, 0, 0, -2, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -5, -24, -3, -2, + -12, -14, 0, 0, 0, 0, 0, 14, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -3, -3, 1, -2, 1, -2, -8, + 1, 6, 1, 2, 1, -12, -3, -7, + 0, -5, -11, -5, -8, -12, -11, 0, + -2, -2, -3, -2, 0, -2, -1, 4, + 0, 4, -2, 0, 9, 0, 0, 0, + 0, -2, -3, -3, 0, 0, -8, 0, + -1, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -3, -3, + 0, -4, 0, -3, 3, -5, -5, -2, + 0, -8, -2, -6, -2, -3, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -5, 0, 0, 0, + 0, -4, 0, -3, 0, 0, -1, 0, + -4, -10, 2, 3, 3, -1, -8, 2, + 4, 2, 9, 2, -8, 0, -2, 0, + -2, -12, 0, 0, -9, -8, 0, -5, + 0, -4, 0, -4, 0, -2, 4, 0, + -2, -9, -3, 11, 0, -7, 0, -3, + 2, 0, 0, -10, 0, -2, -1, 0, + -3, 0, 0, -2, 0, -3, -12, -3, + -6, 0, -9, 0, -3, 0, -5, 0, + 2, 0, -3, 0, -3, -9, 0, -3, + 3, 0, -4, 1, 0, -3, -2, 0, + -3, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -2, 0, 0, 0, 0, + 1, 0, -3, -3, 0, 0, 6, 0, + -18, 1, 12, 9, 5, -12, 2, 12, + 0, 11, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0 +}; + + +/*Collect the kern class' data in one place*/ +static const lv_font_fmt_txt_kern_classes_t kern_classes = +{ + .class_pair_values = kern_class_values, + .left_class_mapping = kern_left_class_mapping, + .right_class_mapping = kern_right_class_mapping, + .left_class_cnt = 47, + .right_class_cnt = 37, +}; + +/*-------------------- + * ALL CUSTOM DATA + *--------------------*/ + +#if LVGL_VERSION_MAJOR == 8 +/*Store all the custom data of the font*/ +static lv_font_fmt_txt_glyph_cache_t cache; +#endif + +#if LVGL_VERSION_MAJOR >= 8 +static const lv_font_fmt_txt_dsc_t font_dsc = { +#else +static lv_font_fmt_txt_dsc_t font_dsc = { +#endif + .glyph_bitmap = glyph_bitmap, + .glyph_dsc = glyph_dsc, + .cmaps = cmaps, + .kern_dsc = &kern_classes, + .kern_scale = 16, + .cmap_num = 5, + .bpp = 4, + .kern_classes = 1, + .bitmap_format = 0, +#if LVGL_VERSION_MAJOR == 8 + .cache = &cache +#endif +}; + + + +/*----------------- + * PUBLIC FONT + *----------------*/ + +/*Initialize a public general font descriptor*/ +#if LVGL_VERSION_MAJOR >= 8 +const lv_font_t montserrat_medium_18 = { +#else +lv_font_t montserrat_medium_18 = { +#endif + .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ + .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ + .line_height = 20, /*The maximum line height required by the font*/ + .base_line = 4, /*Baseline measured from the bottom of the line*/ +#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) + .subpx = LV_FONT_SUBPX_NONE, +#endif +#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 + .underline_position = -1, + .underline_thickness = 1, +#endif + .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ +#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 + .fallback = NULL, +#endif + .user_data = NULL, +}; + + + +#endif /*#if MONTSERRAT_MEDIUM_18*/ + diff --git a/main/fonts/montserrat_medium_24.c b/main/fonts/montserrat_medium_24.c index c08ede7..208cb85 100644 --- a/main/fonts/montserrat_medium_24.c +++ b/main/fonts/montserrat_medium_24.c @@ -1,1576 +1,1701 @@ -/******************************************************************************* - * Size: 24 px - * Bpp: 4 - * Opts: --bpp 4 --size 24 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°éûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz ' --format lvgl -o montserrat_medium_24.c --font fa-solid-900.ttf --range 61461 - ******************************************************************************/ - -#ifdef LV_LVGL_H_INCLUDE_SIMPLE -#include "lvgl.h" -#else -#include "lvgl/lvgl.h" -#endif - -#ifndef MONTSERRAT_MEDIUM_24 -#define MONTSERRAT_MEDIUM_24 1 -#endif - -#if MONTSERRAT_MEDIUM_24 - -/*----------------- - * BITMAPS - *----------------*/ - -/*Store the image of the glyphs*/ -static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { - /* U+0020 " " */ - - /* U+0027 "'" */ - 0x7f, 0x87, 0xf7, 0x6f, 0x76, 0xf7, 0x6f, 0x65, - 0xf6, 0x38, 0x30, - - /* U+002E "." */ - 0x4, 0x10, 0x9f, 0xf1, 0xdf, 0xf4, 0x6f, 0xb0, - - /* U+0030 "0" */ - 0x0, 0x1, 0x8d, 0xff, 0xd8, 0x10, 0x0, 0x0, - 0x2e, 0xff, 0xff, 0xff, 0xe2, 0x0, 0x1, 0xff, - 0xe7, 0x33, 0x7e, 0xff, 0x10, 0xb, 0xfe, 0x20, - 0x0, 0x2, 0xef, 0xb0, 0x2f, 0xf5, 0x0, 0x0, - 0x0, 0x5f, 0xf2, 0x7f, 0xe0, 0x0, 0x0, 0x0, - 0xe, 0xf7, 0xaf, 0xb0, 0x0, 0x0, 0x0, 0xb, - 0xfa, 0xcf, 0x90, 0x0, 0x0, 0x0, 0x9, 0xfc, - 0xdf, 0x80, 0x0, 0x0, 0x0, 0x8, 0xfd, 0xcf, - 0x90, 0x0, 0x0, 0x0, 0x9, 0xfc, 0xaf, 0xb0, - 0x0, 0x0, 0x0, 0xb, 0xfa, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0xe, 0xf7, 0x2f, 0xf5, 0x0, 0x0, - 0x0, 0x5f, 0xf2, 0xb, 0xfe, 0x10, 0x0, 0x2, - 0xef, 0xb0, 0x1, 0xff, 0xe7, 0x33, 0x7e, 0xff, - 0x10, 0x0, 0x3e, 0xff, 0xff, 0xff, 0xe2, 0x0, - 0x0, 0x1, 0x7c, 0xee, 0xc7, 0x10, 0x0, - - /* U+0031 "1" */ - 0xdf, 0xff, 0xff, 0x5d, 0xff, 0xff, 0xf5, 0x11, - 0x11, 0xff, 0x50, 0x0, 0xf, 0xf5, 0x0, 0x0, - 0xff, 0x50, 0x0, 0xf, 0xf5, 0x0, 0x0, 0xff, - 0x50, 0x0, 0xf, 0xf5, 0x0, 0x0, 0xff, 0x50, - 0x0, 0xf, 0xf5, 0x0, 0x0, 0xff, 0x50, 0x0, - 0xf, 0xf5, 0x0, 0x0, 0xff, 0x50, 0x0, 0xf, - 0xf5, 0x0, 0x0, 0xff, 0x50, 0x0, 0xf, 0xf5, - 0x0, 0x0, 0xff, 0x50, - - /* U+0032 "2" */ - 0x0, 0x17, 0xce, 0xfe, 0xc6, 0x0, 0x0, 0x7f, - 0xff, 0xff, 0xff, 0xfc, 0x10, 0x6f, 0xfc, 0x63, - 0x35, 0xbf, 0xfa, 0x0, 0x97, 0x0, 0x0, 0x0, - 0xaf, 0xf1, 0x0, 0x0, 0x0, 0x0, 0x3, 0xff, - 0x30, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xf2, 0x0, - 0x0, 0x0, 0x0, 0x8, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x2, 0xff, 0x70, 0x0, 0x0, 0x0, 0x2, - 0xef, 0xc0, 0x0, 0x0, 0x0, 0x2, 0xef, 0xd1, - 0x0, 0x0, 0x0, 0x2, 0xef, 0xd1, 0x0, 0x0, - 0x0, 0x3, 0xef, 0xc1, 0x0, 0x0, 0x0, 0x3, - 0xef, 0xc0, 0x0, 0x0, 0x0, 0x3, 0xff, 0xb0, - 0x0, 0x0, 0x0, 0x4, 0xff, 0xc2, 0x11, 0x11, - 0x11, 0x11, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, - - /* U+0033 "3" */ - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1, 0x11, 0x11, - 0x11, 0x7f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x3f, - 0xf7, 0x0, 0x0, 0x0, 0x0, 0x1e, 0xfa, 0x0, - 0x0, 0x0, 0x0, 0xc, 0xfd, 0x0, 0x0, 0x0, - 0x0, 0x9, 0xfe, 0x20, 0x0, 0x0, 0x0, 0x3, - 0xff, 0xfc, 0x71, 0x0, 0x0, 0x0, 0x3f, 0xff, - 0xff, 0xe3, 0x0, 0x0, 0x0, 0x0, 0x15, 0xef, - 0xe1, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x60, - 0x0, 0x0, 0x0, 0x0, 0xc, 0xf9, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xdf, 0x81, 0xa1, 0x0, 0x0, - 0x0, 0x4f, 0xf5, 0x9f, 0xfa, 0x53, 0x34, 0x9f, - 0xfd, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfd, 0x20, - 0x0, 0x49, 0xdf, 0xfe, 0xb6, 0x0, 0x0, - - /* U+0034 "4" */ - 0x0, 0x0, 0x0, 0x0, 0xd, 0xfb, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xaf, 0xe1, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6, 0xff, 0x30, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x3f, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xdf, 0xb0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xa, 0xfd, 0x10, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xf3, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x3, 0xff, 0x60, 0x0, 0x9d, 0x70, 0x0, - 0x0, 0x1e, 0xfa, 0x0, 0x0, 0xbf, 0x90, 0x0, - 0x0, 0xbf, 0xd0, 0x0, 0x0, 0xbf, 0x90, 0x0, - 0x7, 0xff, 0x41, 0x11, 0x11, 0xbf, 0x91, 0x11, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, - - /* U+0035 "5" */ - 0x0, 0x8f, 0xff, 0xff, 0xff, 0xff, 0x0, 0xa, - 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0, 0xbf, 0x81, - 0x11, 0x11, 0x11, 0x0, 0xd, 0xf6, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xef, 0x40, 0x0, 0x0, 0x0, - 0x0, 0xf, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x2, - 0xff, 0x31, 0x10, 0x0, 0x0, 0x0, 0x3f, 0xff, - 0xff, 0xfe, 0xa3, 0x0, 0x5, 0xff, 0xff, 0xff, - 0xff, 0xf8, 0x0, 0x0, 0x0, 0x0, 0x26, 0xdf, - 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0xb0, - 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x8f, 0xd0, 0x93, 0x0, 0x0, - 0x0, 0x1e, 0xfa, 0x5f, 0xfb, 0x63, 0x24, 0x7e, - 0xff, 0x31, 0xbf, 0xff, 0xff, 0xff, 0xff, 0x50, - 0x0, 0x28, 0xce, 0xfe, 0xc8, 0x10, 0x0, - - /* U+0036 "6" */ - 0x0, 0x0, 0x4a, 0xdf, 0xfe, 0xb5, 0x0, 0x0, - 0xa, 0xff, 0xff, 0xff, 0xff, 0x10, 0x0, 0xcf, - 0xf9, 0x42, 0x23, 0x76, 0x0, 0x8, 0xfe, 0x30, - 0x0, 0x0, 0x0, 0x0, 0xf, 0xf5, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6f, 0xe0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xaf, 0xa0, 0x5b, 0xef, 0xd9, 0x30, - 0x0, 0xbf, 0x9a, 0xff, 0xff, 0xff, 0xf7, 0x0, - 0xdf, 0xff, 0xc4, 0x1, 0x4c, 0xff, 0x40, 0xcf, - 0xfc, 0x0, 0x0, 0x0, 0xcf, 0xc0, 0xbf, 0xf5, - 0x0, 0x0, 0x0, 0x5f, 0xf0, 0x8f, 0xf2, 0x0, - 0x0, 0x0, 0x3f, 0xf1, 0x4f, 0xf4, 0x0, 0x0, - 0x0, 0x4f, 0xf0, 0xd, 0xfc, 0x0, 0x0, 0x0, - 0xbf, 0xb0, 0x4, 0xff, 0xc3, 0x0, 0x3b, 0xff, - 0x30, 0x0, 0x5f, 0xff, 0xff, 0xff, 0xf5, 0x0, - 0x0, 0x1, 0x8d, 0xff, 0xd9, 0x20, 0x0, - - /* U+0037 "7" */ - 0x4f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf6, 0x4f, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xf5, 0x4f, 0xf2, - 0x11, 0x11, 0x11, 0x8f, 0xf1, 0x4f, 0xf0, 0x0, - 0x0, 0x0, 0xef, 0x90, 0x4f, 0xf0, 0x0, 0x0, - 0x5, 0xff, 0x20, 0x2, 0x20, 0x0, 0x0, 0xc, - 0xfa, 0x0, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf3, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xbf, 0xc0, 0x0, - 0x0, 0x0, 0x0, 0x2, 0xff, 0x50, 0x0, 0x0, - 0x0, 0x0, 0x9, 0xfe, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x1f, 0xf7, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x7f, 0xf1, 0x0, 0x0, 0x0, 0x0, 0x0, 0xef, - 0x90, 0x0, 0x0, 0x0, 0x0, 0x6, 0xff, 0x20, - 0x0, 0x0, 0x0, 0x0, 0xd, 0xfb, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x4f, 0xf4, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xbf, 0xd0, 0x0, 0x0, 0x0, - - /* U+0038 "8" */ - 0x0, 0x6, 0xbe, 0xff, 0xd9, 0x20, 0x0, 0x2, - 0xdf, 0xff, 0xff, 0xff, 0xf7, 0x0, 0xd, 0xff, - 0x71, 0x0, 0x4b, 0xff, 0x40, 0x3f, 0xf5, 0x0, - 0x0, 0x0, 0xcf, 0xa0, 0x4f, 0xf1, 0x0, 0x0, - 0x0, 0x9f, 0xc0, 0x2f, 0xf5, 0x0, 0x0, 0x0, - 0xdf, 0x90, 0xa, 0xff, 0x72, 0x1, 0x4c, 0xff, - 0x20, 0x0, 0x8f, 0xff, 0xff, 0xff, 0xd3, 0x0, - 0x4, 0xdf, 0xff, 0xef, 0xff, 0xf8, 0x0, 0x2f, - 0xfc, 0x40, 0x0, 0x18, 0xff, 0x90, 0xaf, 0xd0, - 0x0, 0x0, 0x0, 0x6f, 0xf2, 0xdf, 0x80, 0x0, - 0x0, 0x0, 0xf, 0xf5, 0xdf, 0x80, 0x0, 0x0, - 0x0, 0x1f, 0xf5, 0xaf, 0xe1, 0x0, 0x0, 0x0, - 0x8f, 0xf2, 0x3f, 0xfd, 0x51, 0x0, 0x3a, 0xff, - 0xa0, 0x5, 0xff, 0xff, 0xff, 0xff, 0xfa, 0x0, - 0x0, 0x17, 0xce, 0xff, 0xd9, 0x40, 0x0, - - /* U+0039 "9" */ - 0x0, 0x4, 0xae, 0xfe, 0xc7, 0x0, 0x0, 0x0, - 0xaf, 0xff, 0xff, 0xff, 0xe2, 0x0, 0x8, 0xff, - 0x82, 0x0, 0x4c, 0xfe, 0x10, 0x1f, 0xf6, 0x0, - 0x0, 0x0, 0xcf, 0xa0, 0x3f, 0xf0, 0x0, 0x0, - 0x0, 0x6f, 0xf1, 0x4f, 0xf0, 0x0, 0x0, 0x0, - 0x6f, 0xf5, 0x1f, 0xf6, 0x0, 0x0, 0x0, 0xcf, - 0xf8, 0xa, 0xff, 0x82, 0x0, 0x4c, 0xff, 0xf9, - 0x0, 0xcf, 0xff, 0xff, 0xff, 0x9c, 0xfa, 0x0, - 0x6, 0xbe, 0xfe, 0xa4, 0xd, 0xf8, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xf, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x3f, 0xf2, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xbf, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x8, - 0xff, 0x50, 0x0, 0xa7, 0x31, 0x25, 0xcf, 0xf9, - 0x0, 0x3, 0xff, 0xff, 0xff, 0xff, 0x80, 0x0, - 0x0, 0x7b, 0xdf, 0xec, 0x82, 0x0, 0x0, - - /* U+0041 "A" */ - 0x0, 0x0, 0x0, 0x0, 0xaf, 0xf2, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0xa0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, - 0xff, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xff, 0x5d, 0xf8, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7f, 0xe0, 0x6f, 0xe0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xd, 0xf7, 0x0, 0xef, 0x60, 0x0, - 0x0, 0x0, 0x0, 0x5, 0xff, 0x10, 0x8, 0xfd, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0xa0, 0x0, - 0x1f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xf3, - 0x0, 0x0, 0xaf, 0xc0, 0x0, 0x0, 0x0, 0xa, - 0xfc, 0x0, 0x0, 0x4, 0xff, 0x30, 0x0, 0x0, - 0x2, 0xff, 0x50, 0x0, 0x0, 0xd, 0xfa, 0x0, - 0x0, 0x0, 0x9f, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xf2, 0x0, 0x0, 0x1f, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0x90, 0x0, 0x7, 0xff, 0x10, 0x0, - 0x0, 0x0, 0x8, 0xff, 0x10, 0x0, 0xef, 0x90, - 0x0, 0x0, 0x0, 0x0, 0x1f, 0xf7, 0x0, 0x5f, - 0xf2, 0x0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe0, - 0xc, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, - 0xff, 0x50, - - /* U+0042 "B" */ - 0x7f, 0xff, 0xff, 0xff, 0xfe, 0xb6, 0x0, 0x7, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xfd, 0x10, 0x7f, - 0xe0, 0x0, 0x0, 0x2, 0x9f, 0xfa, 0x7, 0xfe, - 0x0, 0x0, 0x0, 0x0, 0x9f, 0xf0, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x5, 0xff, 0x7, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x9f, 0xd0, 0x7f, 0xe0, 0x0, - 0x0, 0x2, 0x9f, 0xf5, 0x7, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xf6, 0x0, 0x7f, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xd4, 0x7, 0xfe, 0x0, 0x0, 0x0, - 0x14, 0xcf, 0xf3, 0x7f, 0xe0, 0x0, 0x0, 0x0, - 0x0, 0xdf, 0xa7, 0xfe, 0x0, 0x0, 0x0, 0x0, - 0x8, 0xfd, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x8f, 0xe7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0xc, - 0xfc, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x3b, 0xff, - 0x67, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x90, - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xd9, 0x30, 0x0, - - /* U+0043 "C" */ - 0x0, 0x0, 0x5, 0xad, 0xff, 0xda, 0x50, 0x0, - 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfd, 0x30, - 0x0, 0x5f, 0xff, 0xb6, 0x43, 0x59, 0xff, 0xf2, - 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0x1c, 0x80, - 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x5f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xdf, 0x90, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x9f, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x5f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0x1c, 0x80, - 0x0, 0x5f, 0xff, 0xb5, 0x33, 0x49, 0xff, 0xf2, - 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfd, 0x30, - 0x0, 0x0, 0x5, 0xae, 0xff, 0xda, 0x50, 0x0, - - /* U+0044 "D" */ - 0x7f, 0xff, 0xff, 0xff, 0xfd, 0x94, 0x0, 0x0, - 0x7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x20, - 0x0, 0x7f, 0xe1, 0x11, 0x12, 0x36, 0xbf, 0xff, - 0x40, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x4e, - 0xfe, 0x20, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x2f, 0xfb, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7f, 0xf2, 0x7f, 0xe0, 0x0, 0x0, 0x0, - 0x0, 0x1, 0xff, 0x77, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xd, 0xf9, 0x7f, 0xe0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xcf, 0xa7, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xd, 0xf9, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0x0, 0x1, 0xff, 0x77, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf2, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x0, 0x2f, 0xfb, 0x7, 0xfe, - 0x0, 0x0, 0x0, 0x0, 0x3e, 0xfe, 0x20, 0x7f, - 0xe1, 0x11, 0x11, 0x35, 0xbf, 0xff, 0x40, 0x7, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x20, 0x0, - 0x7f, 0xff, 0xff, 0xff, 0xfd, 0x94, 0x0, 0x0, - 0x0, - - /* U+0045 "E" */ - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x67, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xf6, 0x7f, 0xe1, 0x11, - 0x11, 0x11, 0x11, 0x7, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, - 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0xff, - 0xff, 0xff, 0xff, 0x50, 0x7f, 0xff, 0xff, 0xff, - 0xff, 0xf5, 0x7, 0xfe, 0x11, 0x11, 0x11, 0x11, - 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, - 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x7f, 0xe1, 0x11, 0x11, 0x11, - 0x11, 0x17, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfb, - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xb0, - - /* U+0046 "F" */ - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x67, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xf6, 0x7f, 0xe1, 0x11, - 0x11, 0x11, 0x11, 0x7, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, - 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x7f, 0xff, 0xff, 0xff, - 0xff, 0xf5, 0x7, 0xff, 0xff, 0xff, 0xff, 0xff, - 0x50, 0x7f, 0xe1, 0x11, 0x11, 0x11, 0x10, 0x7, - 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, - 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, - - /* U+0047 "G" */ - 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, - 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfe, 0x50, - 0x0, 0x5f, 0xff, 0xb6, 0x43, 0x48, 0xef, 0xf5, - 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0x9, 0xb0, - 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x5f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xdf, 0x90, 0x0, 0x0, 0x0, 0x0, 0x7, 0x94, - 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x5f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x0, 0x5f, 0xff, 0xb6, 0x32, 0x47, 0xdf, 0xf7, - 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xff, 0x80, - 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x71, 0x0, - - /* U+0048 "H" */ - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, - 0xfe, 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, - 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xfe, - 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xf7, 0xfe, 0x11, 0x11, 0x11, - 0x11, 0x17, 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, - 0x0, 0x7f, 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, - 0x7, 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x7f, 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x7, - 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, - 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf0, - - /* U+0049 "I" */ - 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, - 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, - 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, - 0x7f, 0xe0, - - /* U+004A "J" */ - 0x0, 0x8f, 0xff, 0xff, 0xff, 0xf0, 0x8, 0xff, - 0xff, 0xff, 0xff, 0x0, 0x1, 0x11, 0x11, 0x7f, - 0xf0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xf0, 0x0, 0x0, 0x0, 0x7, - 0xff, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf0, 0x0, - 0x0, 0x0, 0x7, 0xff, 0x0, 0x0, 0x0, 0x0, - 0x7f, 0xf0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x0, - 0x0, 0x0, 0x0, 0x7f, 0xf0, 0x0, 0x0, 0x0, - 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xd0, - 0x5a, 0x0, 0x0, 0xd, 0xfa, 0xf, 0xfc, 0x41, - 0x3b, 0xff, 0x50, 0x5f, 0xff, 0xff, 0xff, 0xa0, - 0x0, 0x29, 0xdf, 0xfc, 0x60, 0x0, - - /* U+004B "K" */ - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x6, 0xff, 0x50, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x6f, 0xf6, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x5, 0xff, 0x60, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x5f, 0xf7, 0x0, 0x0, - 0x7f, 0xe0, 0x0, 0x4, 0xff, 0x80, 0x0, 0x0, - 0x7f, 0xe0, 0x0, 0x4f, 0xf9, 0x0, 0x0, 0x0, - 0x7f, 0xe0, 0x3, 0xff, 0xa0, 0x0, 0x0, 0x0, - 0x7f, 0xe0, 0x3f, 0xfd, 0x0, 0x0, 0x0, 0x0, - 0x7f, 0xe2, 0xef, 0xff, 0x40, 0x0, 0x0, 0x0, - 0x7f, 0xfe, 0xfd, 0xdf, 0xf2, 0x0, 0x0, 0x0, - 0x7f, 0xff, 0xd1, 0x2f, 0xfd, 0x10, 0x0, 0x0, - 0x7f, 0xfe, 0x10, 0x4, 0xff, 0xb0, 0x0, 0x0, - 0x7f, 0xf2, 0x0, 0x0, 0x6f, 0xf8, 0x0, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x8, 0xff, 0x50, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0xbf, 0xf3, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0xc, 0xfe, 0x10, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x1, 0xef, 0xc0, - - /* U+004C "L" */ - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, - 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, - 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, - 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x7f, 0xe1, 0x11, 0x11, 0x11, - 0x11, 0x7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0, - - /* U+004D "M" */ - 0x7f, 0xc0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xdf, 0x57, 0xff, 0x50, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7f, 0xf6, 0x7f, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x1f, 0xff, 0x67, 0xff, 0xf8, 0x0, - 0x0, 0x0, 0x0, 0x9, 0xff, 0xf6, 0x7f, 0xff, - 0xf2, 0x0, 0x0, 0x0, 0x3, 0xff, 0xff, 0x67, - 0xfd, 0xbf, 0xb0, 0x0, 0x0, 0x0, 0xcf, 0x8e, - 0xf6, 0x7f, 0xd2, 0xff, 0x40, 0x0, 0x0, 0x5f, - 0xe0, 0xef, 0x67, 0xfd, 0x8, 0xfd, 0x0, 0x0, - 0xe, 0xf6, 0xe, 0xf6, 0x7f, 0xd0, 0xe, 0xf7, - 0x0, 0x8, 0xfc, 0x0, 0xef, 0x67, 0xfd, 0x0, - 0x5f, 0xf1, 0x1, 0xff, 0x30, 0xe, 0xf6, 0x7f, - 0xd0, 0x0, 0xbf, 0xa0, 0xaf, 0x90, 0x0, 0xef, - 0x67, 0xfd, 0x0, 0x2, 0xff, 0x7f, 0xe1, 0x0, - 0xe, 0xf6, 0x7f, 0xd0, 0x0, 0x8, 0xff, 0xf6, - 0x0, 0x0, 0xef, 0x67, 0xfd, 0x0, 0x0, 0xe, - 0xfd, 0x0, 0x0, 0xe, 0xf6, 0x7f, 0xd0, 0x0, - 0x0, 0x5f, 0x40, 0x0, 0x0, 0xef, 0x67, 0xfd, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xe, 0xf6, - 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xef, 0x60, - - /* U+004E "N" */ - 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, - 0xff, 0xa0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, - 0xff, 0x70, 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xff, - 0xff, 0x40, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xfd, - 0xfe, 0x20, 0x0, 0x0, 0x7f, 0xf7, 0xfe, 0x3f, - 0xfd, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xe0, 0x5f, - 0xfa, 0x0, 0x0, 0x7f, 0xf7, 0xfe, 0x0, 0x8f, - 0xf7, 0x0, 0x7, 0xff, 0x7f, 0xe0, 0x0, 0xbf, - 0xf4, 0x0, 0x7f, 0xf7, 0xfe, 0x0, 0x1, 0xef, - 0xe1, 0x7, 0xff, 0x7f, 0xe0, 0x0, 0x3, 0xff, - 0xc0, 0x7f, 0xf7, 0xfe, 0x0, 0x0, 0x6, 0xff, - 0xa7, 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x9, 0xff, - 0xdf, 0xf7, 0xfe, 0x0, 0x0, 0x0, 0xc, 0xff, - 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x1e, 0xff, - 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xff, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x6f, 0xf0, - - /* U+004F "O" */ - 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, - 0x0, 0x0, 0x0, 0x2d, 0xff, 0xff, 0xff, 0xff, - 0xe4, 0x0, 0x0, 0x0, 0x5f, 0xff, 0xb6, 0x33, - 0x5a, 0xff, 0xf7, 0x0, 0x0, 0x3f, 0xfd, 0x30, - 0x0, 0x0, 0x1, 0xcf, 0xf5, 0x0, 0xd, 0xfe, - 0x10, 0x0, 0x0, 0x0, 0x0, 0xcf, 0xf1, 0x4, - 0xff, 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, - 0x70, 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xb, 0xfc, 0xc, 0xfa, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x8f, 0xf0, 0xdf, 0x90, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6, 0xff, 0xc, 0xfa, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xf0, 0x9f, - 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, 0xfc, - 0x5, 0xff, 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, - 0xff, 0x70, 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, - 0x0, 0xcf, 0xf1, 0x0, 0x3f, 0xfd, 0x30, 0x0, - 0x0, 0x1, 0xcf, 0xf5, 0x0, 0x0, 0x5f, 0xff, - 0xb5, 0x33, 0x59, 0xff, 0xf8, 0x0, 0x0, 0x0, - 0x3d, 0xff, 0xff, 0xff, 0xff, 0xe4, 0x0, 0x0, - 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, - 0x0, 0x0, - - /* U+0050 "P" */ - 0x7f, 0xff, 0xff, 0xff, 0xeb, 0x60, 0x0, 0x7, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xd2, 0x0, 0x7f, - 0xe1, 0x11, 0x12, 0x49, 0xff, 0xe1, 0x7, 0xfe, - 0x0, 0x0, 0x0, 0x3, 0xff, 0x90, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x9, 0xfe, 0x7, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x5f, 0xf0, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0x5, 0xff, 0x7, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x9f, 0xe0, 0x7f, 0xe0, 0x0, 0x0, - 0x0, 0x3f, 0xf9, 0x7, 0xfe, 0x11, 0x11, 0x24, - 0x8f, 0xfe, 0x10, 0x7f, 0xff, 0xff, 0xff, 0xff, - 0xfd, 0x20, 0x7, 0xff, 0xff, 0xff, 0xfe, 0xb6, - 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - - /* U+0051 "Q" */ - 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, - 0x0, 0x0, 0x0, 0x2d, 0xff, 0xff, 0xff, 0xff, - 0xe4, 0x0, 0x0, 0x0, 0x5f, 0xff, 0xb6, 0x33, - 0x5a, 0xff, 0xf7, 0x0, 0x0, 0x2f, 0xfd, 0x30, - 0x0, 0x0, 0x2, 0xcf, 0xf5, 0x0, 0xd, 0xfe, - 0x10, 0x0, 0x0, 0x0, 0x0, 0xdf, 0xf1, 0x4, - 0xff, 0x50, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, - 0x70, 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xb, 0xfc, 0xc, 0xfa, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x8f, 0xf0, 0xdf, 0x90, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6, 0xff, 0xc, 0xfa, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xe0, 0xaf, - 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, 0xfc, - 0x5, 0xff, 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, - 0xff, 0x70, 0xe, 0xfd, 0x10, 0x0, 0x0, 0x0, - 0x0, 0xcf, 0xf1, 0x0, 0x4f, 0xfd, 0x20, 0x0, - 0x0, 0x1, 0xbf, 0xf6, 0x0, 0x0, 0x7f, 0xff, - 0xa4, 0x22, 0x48, 0xef, 0xf9, 0x0, 0x0, 0x0, - 0x5f, 0xff, 0xff, 0xff, 0xff, 0xf6, 0x0, 0x0, - 0x0, 0x0, 0x17, 0xce, 0xff, 0xfd, 0x71, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x1, 0xcf, 0xf7, - 0x10, 0x4, 0xc3, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x9f, 0xff, 0xff, 0xff, 0x70, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x3a, 0xef, 0xea, 0x40, - - /* U+0052 "R" */ - 0x7f, 0xff, 0xff, 0xff, 0xeb, 0x60, 0x0, 0x7, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xd2, 0x0, 0x7f, - 0xe1, 0x11, 0x12, 0x49, 0xff, 0xe1, 0x7, 0xfe, - 0x0, 0x0, 0x0, 0x3, 0xff, 0x90, 0x7f, 0xe0, - 0x0, 0x0, 0x0, 0x9, 0xfe, 0x7, 0xfe, 0x0, - 0x0, 0x0, 0x0, 0x5f, 0xf0, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0x5, 0xff, 0x7, 0xfe, 0x0, 0x0, - 0x0, 0x0, 0x9f, 0xe0, 0x7f, 0xe0, 0x0, 0x0, - 0x0, 0x3f, 0xf8, 0x7, 0xfe, 0x11, 0x11, 0x13, - 0x8f, 0xfe, 0x10, 0x7f, 0xff, 0xff, 0xff, 0xff, - 0xfd, 0x20, 0x7, 0xff, 0xff, 0xff, 0xff, 0xfa, - 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x7f, 0xf2, - 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0xcf, 0xd0, - 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x1, 0xef, 0x90, - 0x7, 0xfe, 0x0, 0x0, 0x0, 0x5, 0xff, 0x40, - 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x9, 0xfe, 0x10, - - /* U+0053 "S" */ - 0x0, 0x0, 0x6b, 0xef, 0xfd, 0xa5, 0x0, 0x0, - 0x2e, 0xff, 0xff, 0xff, 0xff, 0xd1, 0x0, 0xef, - 0xe7, 0x21, 0x14, 0x8e, 0xc0, 0x6, 0xff, 0x20, - 0x0, 0x0, 0x0, 0x20, 0x9, 0xfc, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x8, 0xfe, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x3, 0xff, 0xc3, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x7f, 0xff, 0xd9, 0x51, 0x0, 0x0, - 0x0, 0x4, 0xbf, 0xff, 0xff, 0xc5, 0x0, 0x0, - 0x0, 0x1, 0x59, 0xdf, 0xff, 0xb0, 0x0, 0x0, - 0x0, 0x0, 0x2, 0xaf, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xb, 0xfc, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x7, 0xfe, 0x5, 0x80, 0x0, 0x0, 0x0, - 0xc, 0xfb, 0xd, 0xfe, 0x84, 0x21, 0x25, 0xcf, - 0xf4, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xff, 0x60, - 0x0, 0x4, 0x9d, 0xef, 0xec, 0x82, 0x0, - - /* U+0054 "T" */ - 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x11, 0x11, - 0x13, 0xff, 0x51, 0x11, 0x11, 0x0, 0x0, 0x2, - 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, - 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, - 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, - 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, - 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, 0x0, - 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, - 0x2, 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, - 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, - 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, - 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, - 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, - 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, - - /* U+0055 "U" */ - 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x9a, - 0xfc, 0x0, 0x0, 0x0, 0x0, 0xc, 0xf9, 0xaf, - 0xc0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x9a, 0xfc, - 0x0, 0x0, 0x0, 0x0, 0xc, 0xf9, 0xaf, 0xc0, - 0x0, 0x0, 0x0, 0x0, 0xcf, 0x9a, 0xfc, 0x0, - 0x0, 0x0, 0x0, 0xc, 0xf9, 0xaf, 0xc0, 0x0, - 0x0, 0x0, 0x0, 0xcf, 0x9a, 0xfc, 0x0, 0x0, - 0x0, 0x0, 0xc, 0xf9, 0xaf, 0xc0, 0x0, 0x0, - 0x0, 0x0, 0xcf, 0x99, 0xfc, 0x0, 0x0, 0x0, - 0x0, 0xc, 0xf9, 0x9f, 0xd0, 0x0, 0x0, 0x0, - 0x0, 0xdf, 0x87, 0xff, 0x0, 0x0, 0x0, 0x0, - 0xf, 0xf6, 0x3f, 0xf5, 0x0, 0x0, 0x0, 0x5, - 0xff, 0x20, 0xcf, 0xe1, 0x0, 0x0, 0x1, 0xef, - 0xc0, 0x3, 0xff, 0xe7, 0x32, 0x38, 0xef, 0xf3, - 0x0, 0x4, 0xff, 0xff, 0xff, 0xff, 0xe4, 0x0, - 0x0, 0x1, 0x7c, 0xef, 0xec, 0x71, 0x0, 0x0, - - /* U+0056 "V" */ - 0xd, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x8, - 0xfe, 0x0, 0x6f, 0xf3, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xef, 0x70, 0x0, 0xef, 0xa0, 0x0, 0x0, - 0x0, 0x0, 0x6f, 0xf1, 0x0, 0x8, 0xff, 0x10, - 0x0, 0x0, 0x0, 0xc, 0xf9, 0x0, 0x0, 0x1f, - 0xf8, 0x0, 0x0, 0x0, 0x4, 0xff, 0x20, 0x0, - 0x0, 0xaf, 0xe0, 0x0, 0x0, 0x0, 0xbf, 0xb0, - 0x0, 0x0, 0x3, 0xff, 0x50, 0x0, 0x0, 0x2f, - 0xf4, 0x0, 0x0, 0x0, 0xc, 0xfc, 0x0, 0x0, - 0x9, 0xfd, 0x0, 0x0, 0x0, 0x0, 0x5f, 0xf3, - 0x0, 0x0, 0xff, 0x60, 0x0, 0x0, 0x0, 0x0, - 0xef, 0xa0, 0x0, 0x7f, 0xf0, 0x0, 0x0, 0x0, - 0x0, 0x7, 0xff, 0x10, 0xd, 0xf8, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x1f, 0xf8, 0x5, 0xff, 0x20, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe0, 0xcf, - 0xb0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, - 0x9f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xb, 0xff, 0xfd, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x4f, 0xff, 0x60, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xdf, 0xe0, 0x0, 0x0, - 0x0, 0x0, - - /* U+0057 "W" */ - 0x1f, 0xf6, 0x0, 0x0, 0x0, 0x0, 0xaf, 0xe0, - 0x0, 0x0, 0x0, 0x3, 0xff, 0x10, 0xbf, 0xb0, - 0x0, 0x0, 0x0, 0xf, 0xff, 0x30, 0x0, 0x0, - 0x0, 0x8f, 0xc0, 0x6, 0xff, 0x10, 0x0, 0x0, - 0x5, 0xff, 0xf8, 0x0, 0x0, 0x0, 0xd, 0xf6, - 0x0, 0x1f, 0xf6, 0x0, 0x0, 0x0, 0xbf, 0xef, - 0xe0, 0x0, 0x0, 0x3, 0xff, 0x10, 0x0, 0xbf, - 0xb0, 0x0, 0x0, 0x1f, 0xf4, 0xff, 0x30, 0x0, - 0x0, 0x8f, 0xc0, 0x0, 0x6, 0xff, 0x10, 0x0, - 0x6, 0xfd, 0xc, 0xf8, 0x0, 0x0, 0xd, 0xf6, - 0x0, 0x0, 0x1f, 0xf5, 0x0, 0x0, 0xbf, 0x70, - 0x6f, 0xe0, 0x0, 0x3, 0xff, 0x10, 0x0, 0x0, - 0xcf, 0xb0, 0x0, 0x1f, 0xf2, 0x1, 0xff, 0x30, - 0x0, 0x8f, 0xc0, 0x0, 0x0, 0x6, 0xff, 0x0, - 0x6, 0xfd, 0x0, 0xc, 0xf8, 0x0, 0xd, 0xf7, - 0x0, 0x0, 0x0, 0x1f, 0xf5, 0x0, 0xbf, 0x70, - 0x0, 0x6f, 0xe0, 0x3, 0xff, 0x10, 0x0, 0x0, - 0x0, 0xcf, 0xb0, 0x1f, 0xf2, 0x0, 0x1, 0xff, - 0x30, 0x8f, 0xc0, 0x0, 0x0, 0x0, 0x6, 0xff, - 0x6, 0xfc, 0x0, 0x0, 0xb, 0xf8, 0xd, 0xf7, - 0x0, 0x0, 0x0, 0x0, 0x1f, 0xf5, 0xcf, 0x70, - 0x0, 0x0, 0x6f, 0xe3, 0xff, 0x20, 0x0, 0x0, - 0x0, 0x0, 0xcf, 0xcf, 0xf2, 0x0, 0x0, 0x1, - 0xff, 0xbf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0x7, - 0xff, 0xfc, 0x0, 0x0, 0x0, 0xb, 0xff, 0xf7, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0x70, - 0x0, 0x0, 0x0, 0x6f, 0xff, 0x20, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xcf, 0xf1, 0x0, 0x0, 0x0, - 0x1, 0xff, 0xc0, 0x0, 0x0, 0x0, - - /* U+0058 "X" */ - 0x1e, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe1, - 0x3, 0xff, 0x80, 0x0, 0x0, 0x4, 0xff, 0x50, - 0x0, 0x8f, 0xf3, 0x0, 0x0, 0x1e, 0xf9, 0x0, - 0x0, 0xc, 0xfe, 0x10, 0x0, 0xbf, 0xd0, 0x0, - 0x0, 0x2, 0xff, 0xa0, 0x6, 0xff, 0x20, 0x0, - 0x0, 0x0, 0x5f, 0xf6, 0x2f, 0xf6, 0x0, 0x0, - 0x0, 0x0, 0xa, 0xff, 0xdf, 0xb0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xef, 0xfe, 0x10, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x9f, 0xfb, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x4, 0xff, 0xff, 0x60, 0x0, 0x0, - 0x0, 0x0, 0x1e, 0xfa, 0x9f, 0xf2, 0x0, 0x0, - 0x0, 0x0, 0xbf, 0xe1, 0xd, 0xfd, 0x0, 0x0, - 0x0, 0x6, 0xff, 0x40, 0x2, 0xff, 0x90, 0x0, - 0x0, 0x2f, 0xf8, 0x0, 0x0, 0x6f, 0xf5, 0x0, - 0x0, 0xdf, 0xd0, 0x0, 0x0, 0xb, 0xfe, 0x10, - 0x9, 0xff, 0x20, 0x0, 0x0, 0x1, 0xef, 0xb0, - 0x5f, 0xf6, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf7, - - /* U+0059 "Y" */ - 0xc, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x1, 0xff, - 0x50, 0x3f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0xaf, - 0xb0, 0x0, 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x4f, - 0xf2, 0x0, 0x1, 0xef, 0x90, 0x0, 0x0, 0xd, - 0xf8, 0x0, 0x0, 0x6, 0xff, 0x20, 0x0, 0x7, - 0xfe, 0x0, 0x0, 0x0, 0xc, 0xfc, 0x0, 0x1, - 0xff, 0x50, 0x0, 0x0, 0x0, 0x3f, 0xf5, 0x0, - 0xaf, 0xb0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe0, - 0x4f, 0xf2, 0x0, 0x0, 0x0, 0x0, 0x1, 0xef, - 0x9d, 0xf8, 0x0, 0x0, 0x0, 0x0, 0x0, 0x6, - 0xff, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xc, 0xff, 0x50, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x6, 0xff, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x6, 0xff, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6f, 0xf0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x6, 0xff, 0x0, 0x0, 0x0, - 0x0, - - /* U+005A "Z" */ - 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xc, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xb0, 0x11, - 0x11, 0x11, 0x11, 0x11, 0xcf, 0xf2, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x8f, 0xf4, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x5f, 0xf8, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x2f, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xd, 0xfd, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, - 0xff, 0x20, 0x0, 0x0, 0x0, 0x0, 0x8, 0xff, - 0x50, 0x0, 0x0, 0x0, 0x0, 0x4, 0xff, 0x80, - 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0xb0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xdf, 0xd1, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xbf, 0xf3, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x8f, 0xf5, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x4f, 0xfa, 0x11, 0x11, 0x11, 0x11, 0x11, - 0xe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf1, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x10, - - /* U+0061 "a" */ - 0x0, 0x6b, 0xef, 0xfd, 0x81, 0x0, 0x2e, 0xff, - 0xff, 0xff, 0xfe, 0x10, 0xe, 0xb5, 0x10, 0x27, - 0xff, 0xb0, 0x1, 0x0, 0x0, 0x0, 0x6f, 0xf0, - 0x0, 0x0, 0x0, 0x0, 0x1f, 0xf3, 0x0, 0x37, - 0xaa, 0xaa, 0xaf, 0xf4, 0xa, 0xff, 0xff, 0xff, - 0xff, 0xf4, 0x6f, 0xf6, 0x10, 0x0, 0xf, 0xf4, - 0xbf, 0x90, 0x0, 0x0, 0xf, 0xf4, 0xcf, 0x80, - 0x0, 0x0, 0x5f, 0xf4, 0x8f, 0xe2, 0x0, 0x4, - 0xff, 0xf4, 0x1d, 0xff, 0xcb, 0xdf, 0xdf, 0xf4, - 0x1, 0x8d, 0xff, 0xd8, 0xe, 0xf4, - - /* U+0062 "b" */ - 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, - 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, - 0x0, 0x0, 0x0, 0xdf, 0x70, 0x7c, 0xfe, 0xc7, - 0x10, 0x0, 0xdf, 0x9d, 0xff, 0xff, 0xff, 0xe3, - 0x0, 0xdf, 0xff, 0xa3, 0x12, 0x6e, 0xfe, 0x20, - 0xdf, 0xf8, 0x0, 0x0, 0x1, 0xef, 0xa0, 0xdf, - 0xe0, 0x0, 0x0, 0x0, 0x6f, 0xf1, 0xdf, 0x90, - 0x0, 0x0, 0x0, 0x1f, 0xf3, 0xdf, 0x70, 0x0, - 0x0, 0x0, 0xf, 0xf5, 0xdf, 0x90, 0x0, 0x0, - 0x0, 0x1f, 0xf3, 0xdf, 0xe0, 0x0, 0x0, 0x0, - 0x6f, 0xf1, 0xdf, 0xf8, 0x0, 0x0, 0x2, 0xef, - 0xa0, 0xdf, 0xff, 0xa3, 0x12, 0x6e, 0xff, 0x20, - 0xdf, 0x8d, 0xff, 0xff, 0xff, 0xe3, 0x0, 0xdf, - 0x60, 0x7d, 0xfe, 0xc7, 0x10, 0x0, - - /* U+0063 "c" */ - 0x0, 0x3, 0xad, 0xfe, 0xc6, 0x0, 0x0, 0x9f, - 0xff, 0xff, 0xff, 0xc1, 0x9, 0xff, 0x93, 0x12, - 0x7f, 0xfa, 0x4f, 0xf6, 0x0, 0x0, 0x3, 0x91, - 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, - 0x0, 0x0, 0x0, 0x0, 0xff, 0x50, 0x0, 0x0, - 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, - 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf6, - 0x0, 0x0, 0x2, 0x91, 0x9, 0xff, 0x93, 0x12, - 0x7f, 0xfa, 0x0, 0x9f, 0xff, 0xff, 0xff, 0xc1, - 0x0, 0x3, 0xad, 0xfe, 0xc6, 0x0, - - /* U+0064 "d" */ - 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x2f, 0xf3, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x2f, 0xf3, 0x0, 0x5, 0xbe, 0xfe, 0x92, - 0x2f, 0xf3, 0x1, 0xbf, 0xff, 0xff, 0xff, 0x7f, - 0xf3, 0xb, 0xff, 0x93, 0x12, 0x7f, 0xff, 0xf3, - 0x5f, 0xf6, 0x0, 0x0, 0x3, 0xff, 0xf3, 0xbf, - 0xc0, 0x0, 0x0, 0x0, 0x8f, 0xf3, 0xdf, 0x70, - 0x0, 0x0, 0x0, 0x3f, 0xf3, 0xff, 0x50, 0x0, - 0x0, 0x0, 0x1f, 0xf3, 0xdf, 0x70, 0x0, 0x0, - 0x0, 0x3f, 0xf3, 0xbf, 0xb0, 0x0, 0x0, 0x0, - 0x7f, 0xf3, 0x5f, 0xf5, 0x0, 0x0, 0x2, 0xef, - 0xf3, 0xb, 0xff, 0x71, 0x0, 0x5e, 0xff, 0xf3, - 0x1, 0xbf, 0xff, 0xef, 0xff, 0x7f, 0xf3, 0x0, - 0x5, 0xbe, 0xfe, 0xa3, 0xf, 0xf3, - - /* U+0065 "e" */ - 0x0, 0x5, 0xbe, 0xfd, 0xa3, 0x0, 0x0, 0xa, - 0xff, 0xff, 0xff, 0xf8, 0x0, 0xa, 0xfe, 0x61, - 0x2, 0x8f, 0xf7, 0x4, 0xff, 0x20, 0x0, 0x0, - 0x5f, 0xf1, 0xaf, 0x90, 0x0, 0x0, 0x0, 0xcf, - 0x6d, 0xfc, 0xbb, 0xbb, 0xbb, 0xbd, 0xf9, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xad, 0xf6, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xaf, 0xc0, 0x0, 0x0, - 0x0, 0x0, 0x4, 0xff, 0x60, 0x0, 0x0, 0x6, - 0x0, 0xa, 0xff, 0xa3, 0x11, 0x4b, 0xf8, 0x0, - 0x9, 0xff, 0xff, 0xff, 0xff, 0x40, 0x0, 0x3, - 0xad, 0xff, 0xd8, 0x10, 0x0, - - /* U+0066 "f" */ - 0x0, 0x0, 0x8d, 0xfe, 0xa1, 0x0, 0xb, 0xff, - 0xff, 0xf0, 0x0, 0x4f, 0xf5, 0x0, 0x30, 0x0, - 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xc0, 0x0, - 0x0, 0xaf, 0xff, 0xff, 0xff, 0x70, 0x9e, 0xff, - 0xfe, 0xee, 0x60, 0x0, 0x7f, 0xd0, 0x0, 0x0, - 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, - 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, - 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, - 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, - 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, - 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, - 0x0, 0x0, - - /* U+0067 "g" */ - 0x0, 0x5, 0xbe, 0xfe, 0xa3, 0xd, 0xf5, 0x0, - 0xbf, 0xff, 0xff, 0xff, 0x8d, 0xf5, 0xb, 0xff, - 0x93, 0x12, 0x6e, 0xff, 0xf5, 0x4f, 0xf6, 0x0, - 0x0, 0x1, 0xef, 0xf5, 0xbf, 0xc0, 0x0, 0x0, - 0x0, 0x5f, 0xf5, 0xdf, 0x70, 0x0, 0x0, 0x0, - 0xf, 0xf5, 0xff, 0x50, 0x0, 0x0, 0x0, 0xe, - 0xf5, 0xdf, 0x70, 0x0, 0x0, 0x0, 0xf, 0xf5, - 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x5f, 0xf5, 0x4f, - 0xf6, 0x0, 0x0, 0x1, 0xef, 0xf5, 0xa, 0xff, - 0xa3, 0x12, 0x6e, 0xff, 0xf5, 0x0, 0xbf, 0xff, - 0xff, 0xff, 0x8f, 0xf5, 0x0, 0x5, 0xbe, 0xfe, - 0xa3, 0xf, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x2f, 0xf1, 0x3, 0x10, 0x0, 0x0, 0x0, 0xaf, - 0xd0, 0xd, 0xf9, 0x52, 0x11, 0x4b, 0xff, 0x50, - 0xa, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x0, 0x0, - 0x28, 0xce, 0xff, 0xd9, 0x30, 0x0, - - /* U+0068 "h" */ - 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, - 0x0, 0x0, 0x0, 0xd, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, - 0xd, 0xf7, 0x18, 0xdf, 0xfc, 0x70, 0x0, 0xdf, - 0xae, 0xff, 0xff, 0xff, 0xc0, 0xd, 0xff, 0xf8, - 0x31, 0x4a, 0xff, 0x90, 0xdf, 0xf5, 0x0, 0x0, - 0xa, 0xff, 0xd, 0xfc, 0x0, 0x0, 0x0, 0x3f, - 0xf2, 0xdf, 0x80, 0x0, 0x0, 0x1, 0xff, 0x3d, - 0xf7, 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, - 0x0, 0x0, 0x0, 0xff, 0x4d, 0xf7, 0x0, 0x0, - 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x0, - 0xff, 0x4d, 0xf7, 0x0, 0x0, 0x0, 0xf, 0xf4, - 0xdf, 0x70, 0x0, 0x0, 0x0, 0xff, 0x4d, 0xf7, - 0x0, 0x0, 0x0, 0xf, 0xf4, - - /* U+0069 "i" */ - 0xb, 0xf6, 0x2f, 0xfd, 0xb, 0xf7, 0x0, 0x0, - 0x0, 0x0, 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, - 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, - 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, - 0xd, 0xf7, 0xd, 0xf7, - - /* U+006A "j" */ - 0x0, 0x0, 0x9, 0xf8, 0x0, 0x0, 0x1, 0xff, - 0xf0, 0x0, 0x0, 0xa, 0xf8, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xbf, 0x90, 0x0, 0x0, 0xb, 0xf9, 0x0, - 0x0, 0x0, 0xbf, 0x90, 0x0, 0x0, 0xb, 0xf9, - 0x0, 0x0, 0x0, 0xbf, 0x90, 0x0, 0x0, 0xb, - 0xf9, 0x0, 0x0, 0x0, 0xbf, 0x90, 0x0, 0x0, - 0xb, 0xf9, 0x0, 0x0, 0x0, 0xbf, 0x90, 0x0, - 0x0, 0xb, 0xf9, 0x0, 0x0, 0x0, 0xbf, 0x90, - 0x0, 0x0, 0xb, 0xf9, 0x0, 0x0, 0x0, 0xbf, - 0x90, 0x0, 0x0, 0xb, 0xf9, 0x0, 0x0, 0x0, - 0xdf, 0x80, 0x4, 0x20, 0x5f, 0xf4, 0x0, 0xef, - 0xff, 0xfc, 0x0, 0x9, 0xef, 0xe9, 0x0, 0x0, - - /* U+006B "k" */ - 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, - 0x0, 0x0, 0x0, 0xd, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, - 0xd, 0xf7, 0x0, 0x0, 0x3, 0xef, 0xa0, 0xdf, - 0x70, 0x0, 0x3, 0xff, 0xb0, 0xd, 0xf7, 0x0, - 0x4, 0xff, 0xb0, 0x0, 0xdf, 0x70, 0x5, 0xff, - 0xb0, 0x0, 0xd, 0xf7, 0x6, 0xff, 0xb0, 0x0, - 0x0, 0xdf, 0x77, 0xff, 0xf1, 0x0, 0x0, 0xd, - 0xfe, 0xff, 0xff, 0xb0, 0x0, 0x0, 0xdf, 0xff, - 0x87, 0xff, 0x70, 0x0, 0xd, 0xff, 0x70, 0xa, - 0xff, 0x40, 0x0, 0xdf, 0x90, 0x0, 0xd, 0xfe, - 0x10, 0xd, 0xf7, 0x0, 0x0, 0x2e, 0xfc, 0x0, - 0xdf, 0x70, 0x0, 0x0, 0x4f, 0xf9, 0xd, 0xf7, - 0x0, 0x0, 0x0, 0x7f, 0xf5, - - /* U+006C "l" */ - 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, - 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, - 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, - 0xdf, 0x7d, 0xf7, - - /* U+006D "m" */ - 0xdf, 0x61, 0x9d, 0xfe, 0xb5, 0x0, 0x7, 0xcf, - 0xfd, 0x80, 0x0, 0xdf, 0xaf, 0xff, 0xff, 0xff, - 0x92, 0xef, 0xff, 0xff, 0xfd, 0x10, 0xdf, 0xfe, - 0x60, 0x3, 0xcf, 0xff, 0xfa, 0x20, 0x17, 0xff, - 0xa0, 0xdf, 0xf3, 0x0, 0x0, 0xe, 0xff, 0xa0, - 0x0, 0x0, 0x8f, 0xf0, 0xdf, 0xc0, 0x0, 0x0, - 0x9, 0xff, 0x20, 0x0, 0x0, 0x2f, 0xf3, 0xdf, - 0x80, 0x0, 0x0, 0x7, 0xff, 0x0, 0x0, 0x0, - 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x6, 0xfe, - 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, - 0x0, 0x6, 0xfe, 0x0, 0x0, 0x0, 0xf, 0xf4, - 0xdf, 0x70, 0x0, 0x0, 0x6, 0xfe, 0x0, 0x0, - 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x6, - 0xfe, 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, - 0x0, 0x0, 0x6, 0xfe, 0x0, 0x0, 0x0, 0xf, - 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x6, 0xfe, 0x0, - 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, - 0x6, 0xfe, 0x0, 0x0, 0x0, 0xf, 0xf4, - - /* U+006E "n" */ - 0xdf, 0x61, 0x8d, 0xff, 0xc7, 0x0, 0xd, 0xf9, - 0xff, 0xff, 0xff, 0xfc, 0x0, 0xdf, 0xff, 0x61, - 0x2, 0x8f, 0xf9, 0xd, 0xff, 0x40, 0x0, 0x0, - 0x9f, 0xf0, 0xdf, 0xc0, 0x0, 0x0, 0x3, 0xff, - 0x2d, 0xf8, 0x0, 0x0, 0x0, 0x1f, 0xf3, 0xdf, - 0x70, 0x0, 0x0, 0x0, 0xff, 0x4d, 0xf7, 0x0, - 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, - 0x0, 0xff, 0x4d, 0xf7, 0x0, 0x0, 0x0, 0xf, - 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x0, 0xff, 0x4d, - 0xf7, 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, - 0x0, 0x0, 0x0, 0xff, 0x40, - - /* U+006F "o" */ - 0x0, 0x4, 0xad, 0xfe, 0xb5, 0x0, 0x0, 0x0, - 0x9f, 0xff, 0xff, 0xff, 0xc1, 0x0, 0xa, 0xff, - 0x93, 0x12, 0x7f, 0xfd, 0x0, 0x4f, 0xf6, 0x0, - 0x0, 0x3, 0xff, 0x80, 0xaf, 0xc0, 0x0, 0x0, - 0x0, 0x8f, 0xe0, 0xdf, 0x70, 0x0, 0x0, 0x0, - 0x3f, 0xf1, 0xff, 0x50, 0x0, 0x0, 0x0, 0x1f, - 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x3f, 0xf1, - 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x8f, 0xe0, 0x4f, - 0xf6, 0x0, 0x0, 0x3, 0xff, 0x80, 0xa, 0xff, - 0x93, 0x12, 0x7f, 0xfd, 0x0, 0x0, 0x9f, 0xff, - 0xff, 0xff, 0xc1, 0x0, 0x0, 0x4, 0xad, 0xfe, - 0xb5, 0x0, 0x0, - - /* U+0070 "p" */ - 0xdf, 0x61, 0x8d, 0xfe, 0xc7, 0x10, 0x0, 0xdf, - 0x8e, 0xff, 0xff, 0xff, 0xe3, 0x0, 0xdf, 0xff, - 0x92, 0x0, 0x5d, 0xfe, 0x20, 0xdf, 0xf7, 0x0, - 0x0, 0x1, 0xef, 0xa0, 0xdf, 0xd0, 0x0, 0x0, - 0x0, 0x5f, 0xf1, 0xdf, 0x90, 0x0, 0x0, 0x0, - 0x1f, 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, 0xf, - 0xf5, 0xdf, 0x90, 0x0, 0x0, 0x0, 0x1f, 0xf3, - 0xdf, 0xe0, 0x0, 0x0, 0x0, 0x6f, 0xf1, 0xdf, - 0xf8, 0x0, 0x0, 0x2, 0xef, 0xa0, 0xdf, 0xff, - 0xa3, 0x12, 0x6e, 0xff, 0x20, 0xdf, 0x9d, 0xff, - 0xff, 0xff, 0xe3, 0x0, 0xdf, 0x70, 0x7c, 0xfe, - 0xc7, 0x10, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, - 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, - 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, - - /* U+0071 "q" */ - 0x0, 0x5, 0xbe, 0xfe, 0xa2, 0xf, 0xf3, 0x1, - 0xbf, 0xff, 0xff, 0xff, 0x6f, 0xf3, 0xb, 0xff, - 0x93, 0x12, 0x7f, 0xff, 0xf3, 0x5f, 0xf6, 0x0, - 0x0, 0x3, 0xff, 0xf3, 0xbf, 0xc0, 0x0, 0x0, - 0x0, 0x8f, 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, - 0x3f, 0xf3, 0xff, 0x50, 0x0, 0x0, 0x0, 0x1f, - 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x3f, 0xf3, - 0xbf, 0xc0, 0x0, 0x0, 0x0, 0x8f, 0xf3, 0x5f, - 0xf6, 0x0, 0x0, 0x3, 0xff, 0xf3, 0xb, 0xff, - 0x93, 0x12, 0x7f, 0xff, 0xf3, 0x1, 0xbf, 0xff, - 0xff, 0xff, 0x7f, 0xf3, 0x0, 0x5, 0xbe, 0xfe, - 0x92, 0x2f, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x2f, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, - 0xf3, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, - - /* U+0072 "r" */ - 0xdf, 0x61, 0x8d, 0xf0, 0xdf, 0x7e, 0xff, 0xf0, - 0xdf, 0xff, 0xb5, 0x40, 0xdf, 0xf7, 0x0, 0x0, - 0xdf, 0xd0, 0x0, 0x0, 0xdf, 0x90, 0x0, 0x0, - 0xdf, 0x70, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, - 0xdf, 0x70, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, - 0xdf, 0x70, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, - 0xdf, 0x70, 0x0, 0x0, - - /* U+0073 "s" */ - 0x0, 0x18, 0xcf, 0xfe, 0xb7, 0x10, 0x2, 0xef, - 0xff, 0xff, 0xff, 0xb0, 0xb, 0xfe, 0x41, 0x2, - 0x6c, 0x30, 0xf, 0xf5, 0x0, 0x0, 0x0, 0x0, - 0xe, 0xf9, 0x0, 0x0, 0x0, 0x0, 0x8, 0xff, - 0xd9, 0x52, 0x0, 0x0, 0x0, 0x8f, 0xff, 0xff, - 0xe9, 0x10, 0x0, 0x0, 0x47, 0xad, 0xff, 0xc0, - 0x0, 0x0, 0x0, 0x0, 0x5f, 0xf3, 0x1, 0x0, - 0x0, 0x0, 0xf, 0xf4, 0xe, 0xc6, 0x20, 0x3, - 0xaf, 0xf1, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x60, - 0x1, 0x7b, 0xef, 0xfd, 0x92, 0x0, - - /* U+0074 "t" */ - 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, - 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0xaf, - 0xff, 0xff, 0xff, 0x70, 0x9e, 0xff, 0xfe, 0xee, - 0x60, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, - 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, - 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, - 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, - 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, - 0x0, 0x0, 0x4f, 0xf7, 0x1, 0x50, 0x0, 0xc, - 0xff, 0xff, 0xf1, 0x0, 0x0, 0x9e, 0xfd, 0x81, - - /* U+0075 "u" */ - 0xff, 0x60, 0x0, 0x0, 0x4, 0xff, 0xf, 0xf6, - 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xff, 0x60, 0x0, - 0x0, 0x4, 0xff, 0xf, 0xf6, 0x0, 0x0, 0x0, - 0x4f, 0xf0, 0xff, 0x60, 0x0, 0x0, 0x4, 0xff, - 0xf, 0xf6, 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xff, - 0x60, 0x0, 0x0, 0x4, 0xff, 0xe, 0xf6, 0x0, - 0x0, 0x0, 0x5f, 0xf0, 0xdf, 0x80, 0x0, 0x0, - 0x8, 0xff, 0xa, 0xfe, 0x0, 0x0, 0x1, 0xef, - 0xf0, 0x3f, 0xfb, 0x20, 0x4, 0xdf, 0xff, 0x0, - 0x8f, 0xff, 0xff, 0xff, 0x9f, 0xf0, 0x0, 0x4b, - 0xef, 0xea, 0x32, 0xff, 0x0, - - /* U+0076 "v" */ - 0xd, 0xf9, 0x0, 0x0, 0x0, 0x1, 0xff, 0x30, - 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x7f, 0xc0, 0x0, - 0xef, 0x60, 0x0, 0x0, 0xd, 0xf5, 0x0, 0x8, - 0xfd, 0x0, 0x0, 0x5, 0xfe, 0x0, 0x0, 0x2f, - 0xf3, 0x0, 0x0, 0xbf, 0x80, 0x0, 0x0, 0xbf, - 0xa0, 0x0, 0x2f, 0xf1, 0x0, 0x0, 0x4, 0xff, - 0x10, 0x9, 0xfa, 0x0, 0x0, 0x0, 0xd, 0xf7, - 0x1, 0xff, 0x30, 0x0, 0x0, 0x0, 0x6f, 0xe0, - 0x7f, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xff, 0x5d, - 0xf5, 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, 0xfe, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xff, 0x80, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xbf, 0xf1, 0x0, - 0x0, 0x0, - - /* U+0077 "w" */ - 0xaf, 0x80, 0x0, 0x0, 0x5, 0xff, 0x0, 0x0, - 0x0, 0xc, 0xf4, 0x5f, 0xd0, 0x0, 0x0, 0xb, - 0xff, 0x50, 0x0, 0x0, 0x2f, 0xe0, 0xe, 0xf3, - 0x0, 0x0, 0x1f, 0xff, 0xb0, 0x0, 0x0, 0x8f, - 0x80, 0x9, 0xf9, 0x0, 0x0, 0x7f, 0xbf, 0xf1, - 0x0, 0x0, 0xef, 0x20, 0x3, 0xfe, 0x0, 0x0, - 0xcf, 0x4b, 0xf7, 0x0, 0x4, 0xfc, 0x0, 0x0, - 0xdf, 0x40, 0x2, 0xfe, 0x5, 0xfc, 0x0, 0xa, - 0xf6, 0x0, 0x0, 0x7f, 0xa0, 0x8, 0xf8, 0x0, - 0xef, 0x20, 0xf, 0xf1, 0x0, 0x0, 0x2f, 0xf0, - 0xe, 0xf2, 0x0, 0x9f, 0x80, 0x5f, 0xb0, 0x0, - 0x0, 0xc, 0xf5, 0x4f, 0xc0, 0x0, 0x3f, 0xe0, - 0xbf, 0x50, 0x0, 0x0, 0x6, 0xfb, 0xaf, 0x60, - 0x0, 0xd, 0xf5, 0xfe, 0x0, 0x0, 0x0, 0x1, - 0xff, 0xff, 0x0, 0x0, 0x7, 0xff, 0xf9, 0x0, - 0x0, 0x0, 0x0, 0xaf, 0xfa, 0x0, 0x0, 0x1, - 0xff, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf4, - 0x0, 0x0, 0x0, 0xbf, 0xd0, 0x0, 0x0, - - /* U+0078 "x" */ - 0x1e, 0xf8, 0x0, 0x0, 0x4, 0xff, 0x40, 0x4f, - 0xf4, 0x0, 0x1, 0xef, 0x80, 0x0, 0x8f, 0xe1, - 0x0, 0xbf, 0xb0, 0x0, 0x0, 0xcf, 0xb0, 0x7f, - 0xe1, 0x0, 0x0, 0x1, 0xef, 0xaf, 0xf4, 0x0, - 0x0, 0x0, 0x4, 0xff, 0xf7, 0x0, 0x0, 0x0, - 0x0, 0xd, 0xff, 0x10, 0x0, 0x0, 0x0, 0x8, - 0xff, 0xfb, 0x0, 0x0, 0x0, 0x4, 0xff, 0x5e, - 0xf7, 0x0, 0x0, 0x1, 0xef, 0x80, 0x4f, 0xf3, - 0x0, 0x0, 0xcf, 0xc0, 0x0, 0x8f, 0xe1, 0x0, - 0x8f, 0xe1, 0x0, 0x0, 0xcf, 0xb0, 0x4f, 0xf4, - 0x0, 0x0, 0x2, 0xff, 0x80, - - /* U+0079 "y" */ - 0xd, 0xf9, 0x0, 0x0, 0x0, 0x1, 0xff, 0x30, - 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x7f, 0xc0, 0x0, - 0xef, 0x60, 0x0, 0x0, 0xd, 0xf5, 0x0, 0x8, - 0xfd, 0x0, 0x0, 0x4, 0xfe, 0x0, 0x0, 0x2f, - 0xf4, 0x0, 0x0, 0xbf, 0x80, 0x0, 0x0, 0xbf, - 0xb0, 0x0, 0x2f, 0xf1, 0x0, 0x0, 0x4, 0xff, - 0x10, 0x8, 0xfa, 0x0, 0x0, 0x0, 0xd, 0xf8, - 0x0, 0xef, 0x30, 0x0, 0x0, 0x0, 0x6f, 0xe0, - 0x6f, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xef, 0x6c, - 0xf5, 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, 0xfe, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0x70, - 0x0, 0x0, 0x0, 0x0, 0x0, 0xaf, 0xf1, 0x0, - 0x0, 0x0, 0x0, 0x0, 0xa, 0xfa, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, - 0x0, 0xa4, 0x2, 0xcf, 0xb0, 0x0, 0x0, 0x0, - 0x5f, 0xff, 0xff, 0xe1, 0x0, 0x0, 0x0, 0x0, - 0x8d, 0xfe, 0x91, 0x0, 0x0, 0x0, 0x0, - - /* U+007A "z" */ - 0xe, 0xff, 0xff, 0xff, 0xff, 0xf6, 0xd, 0xee, - 0xee, 0xee, 0xff, 0xf5, 0x0, 0x0, 0x0, 0x1, - 0xef, 0xa0, 0x0, 0x0, 0x0, 0xc, 0xfd, 0x0, - 0x0, 0x0, 0x0, 0x8f, 0xf2, 0x0, 0x0, 0x0, - 0x5, 0xff, 0x40, 0x0, 0x0, 0x0, 0x2f, 0xf8, - 0x0, 0x0, 0x0, 0x0, 0xdf, 0xb0, 0x0, 0x0, - 0x0, 0xb, 0xfd, 0x10, 0x0, 0x0, 0x0, 0x7f, - 0xf2, 0x0, 0x0, 0x0, 0x4, 0xff, 0x50, 0x0, - 0x0, 0x0, 0xe, 0xff, 0xee, 0xee, 0xee, 0xe8, - 0xf, 0xff, 0xff, 0xff, 0xff, 0xf9, - - /* U+00B0 "°" */ - 0x0, 0x0, 0x0, 0x0, 0x2, 0xbf, 0xfb, 0x20, - 0x1e, 0xc5, 0x5c, 0xe2, 0x9d, 0x0, 0x0, 0xda, - 0xd8, 0x0, 0x0, 0x7e, 0xd7, 0x0, 0x0, 0x7e, - 0xac, 0x0, 0x0, 0xcb, 0x3f, 0xa2, 0x2a, 0xf3, - 0x4, 0xef, 0xfe, 0x40, 0x0, 0x2, 0x20, 0x0, - - /* U+00E9 "é" */ - 0x0, 0x0, 0x0, 0xa, 0xfe, 0x30, 0x0, 0x0, - 0x0, 0xa, 0xfc, 0x10, 0x0, 0x0, 0x0, 0xa, - 0xf9, 0x0, 0x0, 0x0, 0x0, 0x1, 0x33, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x5b, 0xef, 0xda, 0x30, 0x0, 0x0, - 0xaf, 0xff, 0xff, 0xff, 0x80, 0x0, 0xaf, 0xe6, - 0x10, 0x28, 0xff, 0x70, 0x4f, 0xf2, 0x0, 0x0, - 0x5, 0xff, 0x1a, 0xf9, 0x0, 0x0, 0x0, 0xc, - 0xf6, 0xdf, 0xcb, 0xbb, 0xbb, 0xbb, 0xdf, 0x9f, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, 0xdf, 0x60, - 0x0, 0x0, 0x0, 0x0, 0xa, 0xfc, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x4f, 0xf6, 0x0, 0x0, 0x0, - 0x60, 0x0, 0xaf, 0xfa, 0x31, 0x14, 0xbf, 0x80, - 0x0, 0x9f, 0xff, 0xff, 0xff, 0xf4, 0x0, 0x0, - 0x3a, 0xdf, 0xfd, 0x81, 0x0, - - /* U+00FB "û" */ - 0x0, 0x0, 0x8f, 0xfa, 0x0, 0x0, 0x0, 0x0, - 0x9f, 0xba, 0xfa, 0x0, 0x0, 0x0, 0x9f, 0x90, - 0x7, 0xfa, 0x0, 0x0, 0x2, 0x20, 0x0, 0x1, - 0x20, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0xf, 0xf6, 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xff, - 0x60, 0x0, 0x0, 0x4, 0xff, 0xf, 0xf6, 0x0, - 0x0, 0x0, 0x4f, 0xf0, 0xff, 0x60, 0x0, 0x0, - 0x4, 0xff, 0xf, 0xf6, 0x0, 0x0, 0x0, 0x4f, - 0xf0, 0xff, 0x60, 0x0, 0x0, 0x4, 0xff, 0xf, - 0xf6, 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xef, 0x60, - 0x0, 0x0, 0x5, 0xff, 0xd, 0xf8, 0x0, 0x0, - 0x0, 0x8f, 0xf0, 0xaf, 0xe0, 0x0, 0x0, 0x1e, - 0xff, 0x3, 0xff, 0xb2, 0x0, 0x4d, 0xff, 0xf0, - 0x8, 0xff, 0xff, 0xff, 0xf9, 0xff, 0x0, 0x4, - 0xbe, 0xfe, 0xa3, 0x2f, 0xf0, - - /* U+F015 "" */ - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x9f, 0x90, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x1c, 0xff, 0xfb, 0x10, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, 0xdf, - 0xff, 0xff, 0xd1, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x3e, 0xff, 0xff, 0xff, - 0xfe, 0x30, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, - 0x0, 0x4, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf4, - 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x6f, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x60, 0x0, - 0x0, 0x0, 0x0, 0x0, 0x8, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xf8, 0x0, 0x0, 0x0, - 0x0, 0x0, 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0x90, 0x0, 0x0, 0x0, 0x1c, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xfb, 0x0, 0x0, 0x2, 0xdf, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xd1, 0x0, 0x3e, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x20, - 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xd0, 0xdf, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xd0, 0x27, 0x8f, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0x87, 0x10, 0x0, 0xf, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0, 0x0, - 0x0, 0xf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, - 0xff, 0xff, 0xff, 0xfa, 0x88, 0x8a, 0xff, 0xff, - 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, 0xff, 0xff, - 0xff, 0xa0, 0x0, 0x0, 0xaf, 0xff, 0xff, 0xff, - 0x0, 0x0, 0x0, 0xf, 0xff, 0xff, 0xff, 0x80, - 0x0, 0x0, 0x8f, 0xff, 0xff, 0xff, 0x0, 0x0, - 0x0, 0xf, 0xff, 0xff, 0xff, 0x80, 0x0, 0x0, - 0x8f, 0xff, 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, - 0xff, 0xff, 0xff, 0x80, 0x0, 0x0, 0x8f, 0xff, - 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, 0xff, 0xff, - 0xff, 0x80, 0x0, 0x0, 0x8f, 0xff, 0xff, 0xff, - 0x0, 0x0, 0x0, 0xe, 0xff, 0xff, 0xff, 0x60, - 0x0, 0x0, 0x6f, 0xff, 0xff, 0xfe, 0x0, 0x0, - 0x0, 0x5, 0xef, 0xff, 0xfb, 0x0, 0x0, 0x0, - 0xb, 0xff, 0xff, 0xe5, 0x0, 0x0 -}; - - -/*--------------------- - * GLYPH DESCRIPTION - *--------------------*/ - -static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { - {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, - {.bitmap_index = 0, .adv_w = 103, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 0, .adv_w = 81, .box_w = 3, .box_h = 7, .ofs_x = 1, .ofs_y = 10}, - {.bitmap_index = 11, .adv_w = 87, .box_w = 4, .box_h = 4, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 19, .adv_w = 256, .box_w = 14, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 138, .adv_w = 142, .box_w = 7, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 198, .adv_w = 220, .box_w = 13, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 309, .adv_w = 220, .box_w = 13, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 420, .adv_w = 257, .box_w = 16, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 556, .adv_w = 220, .box_w = 13, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 667, .adv_w = 237, .box_w = 14, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 786, .adv_w = 230, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 905, .adv_w = 247, .box_w = 14, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1024, .adv_w = 237, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 1143, .adv_w = 281, .box_w = 19, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 1305, .adv_w = 291, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 1433, .adv_w = 278, .box_w = 16, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1569, .adv_w = 317, .box_w = 17, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 1714, .adv_w = 257, .box_w = 13, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 1825, .adv_w = 244, .box_w = 13, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 1936, .adv_w = 296, .box_w = 16, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 2072, .adv_w = 312, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 2200, .adv_w = 119, .box_w = 3, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 2226, .adv_w = 197, .box_w = 11, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 2320, .adv_w = 276, .box_w = 16, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 2456, .adv_w = 228, .box_w = 13, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 2567, .adv_w = 367, .box_w = 19, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 2729, .adv_w = 312, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 2857, .adv_w = 323, .box_w = 19, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 3019, .adv_w = 277, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 3147, .adv_w = 323, .box_w = 19, .box_h = 20, .ofs_x = 1, .ofs_y = -3}, - {.bitmap_index = 3337, .adv_w = 279, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 3465, .adv_w = 238, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3584, .adv_w = 225, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 3703, .adv_w = 304, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 3831, .adv_w = 273, .box_w = 19, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 3993, .adv_w = 432, .box_w = 27, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 4223, .adv_w = 258, .box_w = 16, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 4359, .adv_w = 248, .box_w = 17, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 4504, .adv_w = 252, .box_w = 15, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 4632, .adv_w = 230, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 4710, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 4836, .adv_w = 219, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 4914, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 5040, .adv_w = 235, .box_w = 13, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 5125, .adv_w = 136, .box_w = 10, .box_h = 18, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 5215, .adv_w = 265, .box_w = 14, .box_h = 18, .ofs_x = 1, .ofs_y = -5}, - {.bitmap_index = 5341, .adv_w = 262, .box_w = 13, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 5458, .adv_w = 107, .box_w = 4, .box_h = 18, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 5494, .adv_w = 109, .box_w = 9, .box_h = 23, .ofs_x = -3, .ofs_y = -5}, - {.bitmap_index = 5598, .adv_w = 237, .box_w = 13, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 5715, .adv_w = 107, .box_w = 3, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 5742, .adv_w = 406, .box_w = 22, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 5885, .adv_w = 262, .box_w = 13, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 5970, .adv_w = 244, .box_w = 14, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 6061, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 2, .ofs_y = -5}, - {.bitmap_index = 6187, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 1, .ofs_y = -5}, - {.bitmap_index = 6313, .adv_w = 157, .box_w = 8, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 6365, .adv_w = 192, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 6443, .adv_w = 159, .box_w = 10, .box_h = 16, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 6523, .adv_w = 260, .box_w = 13, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 6608, .adv_w = 215, .box_w = 15, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, - {.bitmap_index = 6706, .adv_w = 345, .box_w = 22, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 6849, .adv_w = 212, .box_w = 13, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 6934, .adv_w = 215, .box_w = 15, .box_h = 18, .ofs_x = -1, .ofs_y = -5}, - {.bitmap_index = 7069, .adv_w = 200, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 7147, .adv_w = 161, .box_w = 8, .box_h = 10, .ofs_x = 1, .ofs_y = 9}, - {.bitmap_index = 7187, .adv_w = 235, .box_w = 13, .box_h = 18, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 7304, .adv_w = 260, .box_w = 13, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 7421, .adv_w = 432, .box_w = 28, .box_h = 25, .ofs_x = 0, .ofs_y = -3} -}; - -/*--------------------- - * CHARACTER MAPPING - *--------------------*/ - -static const uint16_t unicode_list_0[] = { - 0x0, 0x7, 0xe -}; - -static const uint16_t unicode_list_4[] = { - 0x0, 0x39, 0x4b, 0xef65 -}; - -/*Collect the unicode lists and glyph_id offsets*/ -static const lv_font_fmt_txt_cmap_t cmaps[] = -{ - { - .range_start = 32, .range_length = 15, .glyph_id_start = 1, - .unicode_list = unicode_list_0, .glyph_id_ofs_list = NULL, .list_length = 3, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - }, - { - .range_start = 48, .range_length = 10, .glyph_id_start = 4, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 65, .range_length = 26, .glyph_id_start = 14, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 97, .range_length = 26, .glyph_id_start = 40, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 176, .range_length = 61286, .glyph_id_start = 66, - .unicode_list = unicode_list_4, .glyph_id_ofs_list = NULL, .list_length = 4, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - } -}; - -/*----------------- - * KERNING - *----------------*/ - - -/*Map glyph_ids to kern left classes*/ -static const uint8_t kern_left_class_mapping[] = -{ - 0, 0, 1, 2, 3, 0, 4, 5, - 6, 7, 8, 9, 10, 3, 11, 12, - 13, 14, 15, 16, 17, 18, 18, 19, - 20, 21, 18, 18, 14, 22, 14, 23, - 24, 25, 19, 26, 26, 27, 28, 29, - 30, 31, 32, 33, 34, 35, 36, 30, - 36, 36, 37, 33, 30, 30, 31, 31, - 38, 39, 40, 41, 36, 42, 42, 43, - 42, 44, 45, 34, 36, 0 -}; - -/*Map glyph_ids to kern right classes*/ -static const uint8_t kern_right_class_mapping[] = -{ - 0, 0, 1, 2, 3, 4, 5, 6, - 7, 8, 3, 9, 10, 11, 12, 13, - 14, 13, 13, 13, 14, 13, 13, 15, - 13, 13, 13, 13, 14, 13, 14, 13, - 16, 17, 18, 19, 19, 20, 21, 22, - 23, 24, 25, 25, 25, 0, 25, 24, - 26, 27, 24, 24, 28, 28, 25, 28, - 25, 28, 29, 30, 31, 32, 32, 33, - 32, 34, 35, 25, 31, 0 -}; - -/*Kern values between classes*/ -static const int8_t kern_class_values[] = -{ - 17, -21, 3, 18, 8, 7, -15, 3, - 19, 1, 16, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 8, -21, 0, -5, -5, 4, - 4, -3, 0, -5, 4, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -24, 3, -5, - 0, -1, -1, -4, 0, 0, -3, 0, - 0, -3, 0, 0, -9, 0, -8, 0, - -10, -13, -13, -7, 0, 0, 0, 0, - -3, 0, 0, 4, 0, 3, -4, 0, - 1, 0, 4, -1, 0, 0, 0, -7, - 0, -1, 0, 0, 1, 0, 0, 5, - 0, -3, 0, -5, 0, -7, 0, 0, - 0, -4, 0, 0, 0, 0, 0, -1, - 1, -3, -3, 0, -4, 0, 0, 0, - -2, -2, 0, -4, -5, 0, 0, 1, - 0, 0, 0, 0, -3, 0, -4, -4, - -4, 0, 0, 0, 0, 0, -2, 0, - 0, 0, 0, -3, -5, 0, -6, -12, - 8, 0, -10, -1, -5, 0, -1, -18, - 4, -3, 0, 0, 4, 1, -3, -20, - 0, -20, -3, -33, -3, 11, 0, 5, - 0, 0, 0, 0, 1, 0, -7, -5, - 0, -12, 0, 0, 0, 0, -2, -2, - 0, -2, -5, 0, 0, 0, 0, 0, - -4, 0, -4, 0, -3, -5, -3, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -3, -3, 0, -5, -3, 4, 0, - 0, 0, 0, 0, 0, -3, 0, 0, - 3, 0, 0, 0, 0, -4, 0, -4, - -3, -5, 0, 0, 0, 3, 0, -3, - 0, 0, 0, 0, -4, -6, 0, -7, - 12, -20, -8, 4, 0, -3, -25, -7, - 0, -7, 0, -25, 0, -7, -10, -3, - 0, 0, 2, -1, 3, -3, -15, 0, - -19, -9, -8, -9, -12, -5, -10, -1, - -7, -10, 2, 1, 4, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -2, 0, - 0, -1, 0, -4, 0, -7, -8, -8, - -1, 0, 0, 0, 0, -3, 0, 0, - 0, 0, 2, -2, 0, 0, -17, 13, - -3, -16, 0, 4, -6, 0, -19, -2, - -5, 5, 0, -4, 6, 0, -13, -6, - -14, -13, -16, 0, 0, 0, -2, 0, - 0, 0, -2, -2, -4, -10, -13, -1, - -36, 0, 1, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -4, 0, -2, -4, -6, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 5, -8, 4, - -3, -1, -10, -4, 0, -5, -4, -7, - 0, -6, 0, -1, -3, -1, -3, -7, - -5, 0, -3, 0, -8, 0, 0, 0, - -8, 0, -7, 0, -7, -7, 4, -7, - -8, 0, -4, -4, -5, 0, 0, 0, - 0, 0, -4, 0, 0, -6, 0, -4, - 0, -8, -10, -12, -3, 0, 0, 0, - 0, 31, 0, 0, 2, 0, 0, -5, - 0, 4, 0, 4, -5, 0, -3, -5, - -12, -3, -3, -3, -1, 0, 0, -1, - 0, 0, 0, 0, -4, -3, -3, 0, - -3, 0, -3, 0, 0, 0, -3, -5, - -3, -3, -5, -3, 0, 15, -4, -5, - 6, 0, 0, -18, -7, 4, -7, 3, - -12, 0, -3, -6, -1, 2, 0, 0, - -7, 0, 0, -7, 0, -7, -4, -6, - -4, -4, 0, -7, 2, -7, -7, 12, - 0, 4, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -3, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, -3, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -6, 0, 0, 0, 0, -5, 0, - 0, -4, -4, 0, 0, 0, 0, 0, - -2, 0, 0, 0, 0, 0, -3, 0, - 0, 0, 0, -8, 8, 1, -3, -18, - 0, 0, -8, -4, -11, 0, -10, 0, - -6, -17, -4, -15, -15, -18, 0, -5, - 0, -9, -4, -1, -4, -7, -10, -7, - -14, -16, -9, -4, 0, 12, -8, -14, - 0, 1, -12, 0, -19, -3, -4, 1, - 0, -5, 0, -3, -25, -5, -20, -4, - -28, 0, 1, 0, -3, 0, 0, 0, - 0, -2, -3, -15, -3, 0, -25, 0, - -11, 0, 0, -2, -6, -12, -4, 0, - -3, 0, -17, -4, 0, -13, 0, -12, - -3, -7, -10, -4, -7, -6, 0, -5, - -7, -4, -7, 0, 2, 0, -3, -13, - 0, 8, 0, 0, 0, 0, 0, -3, - -8, 0, 0, 0, 0, 0, 0, 0, - -4, 0, -4, 0, 0, -8, -4, 0, - -2, 0, 0, 0, 0, 0, 0, 2, - 0, 0, 0, 0, 6, -12, 8, 0, - -4, 0, -3, 4, 0, -4, 0, -4, - 0, 0, 0, 0, 0, -4, 0, 0, - -5, -6, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -4, -4, 0, -6, - 3, -12, -8, 15, 7, 4, -33, -3, - 8, -4, 0, -13, 0, -4, -4, -3, - 4, -5, -3, -12, -3, 0, -11, 0, - -21, -5, 11, -5, -15, 1, -5, -13, - -13, -4, 15, 0, -14, -10, 12, 0, - 1, -28, -3, 4, -7, -3, -14, -6, - -8, -6, -6, -3, 0, 0, -9, -8, - -4, -21, 0, -21, -5, 0, -13, -22, - -1, -12, -7, -13, -11, 10, 0, 0, - -13, 4, 0, 0, -20, 0, -4, -8, - -7, -13, -9, -10, 0, -5, -12, -4, - -9, -7, -12, -4, -7, 0, -12, -4, - 0, -4, -8, -9, -10, -11, -15, -5, - -8, 0, -14, -13, 13, -4, 2, -36, - -7, 8, -8, -7, -16, -5, -12, -4, - -6, -3, -4, -8, -12, -1, 0, -25, - 0, -23, -9, 9, -15, -26, -8, -13, - -16, -19, -13, 8, 0, 8, -7, 8, - 0, 0, -12, -1, 0, -1, 0, 0, - 0, -3, 0, 0, 0, 0, 0, -4, - 0, 0, 1, 0, -5, 0, 0, 0, - 0, -3, -3, -5, 0, 0, 0, 0, - 0, 0, -8, -2, 0, 0, 0, -8, - 0, -5, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, -4, 0, - 0, -7, -6, -5, 0, -10, -4, -9, - 0, 0, -10, 0, -4, -4, 0, 0, - 0, 0, -31, -7, -15, -4, -14, 0, - -2, 0, 0, 0, 0, 0, 0, 0, - 0, -6, -7, -3, -7, 0, 8, -3, - -9, -3, -7, -7, 0, -5, -2, -3, - 0, 0, -1, 0, 0, -34, -3, -5, - 0, -8, 0, 0, -3, -3, 0, 0, - 0, 0, 3, 0, -3, -7, -3, 7, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 5, 0, 0, - 0, 0, 0, -8, 0, 0, -10, -4, - -8, 0, 0, -11, 0, -4, 0, 0, - 0, 0, 0, -37, 0, -8, -14, -19, - 0, -6, 0, 0, 0, 0, 0, 0, - 0, 0, -4, -6, -2, -6, 0, -4, - 5, 19, 7, 8, -10, 5, 16, 5, - 11, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -4, 0, -3, 31, - 17, 31, 0, 0, 0, 4, 0, 0, - 14, 0, 0, 0, -3, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -6, -32, -5, -3, -16, -19, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 4, -4, 3, - 7, 4, -12, 0, -1, -3, 4, 0, - 0, 0, 0, 0, -10, 0, -3, -3, - -8, 0, -4, 0, -8, -3, 0, -3, - -7, 0, -4, -11, -8, -5, 0, 0, - 0, 0, -3, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -6, -32, - -5, -3, -16, -19, 0, 0, 0, 0, - 0, 19, 0, 0, 0, 0, 0, 0, - 0, 0, 0, -4, 1, -2, 1, -3, - -10, 1, 8, 1, 3, -15, -5, -9, - 0, -6, -15, -7, -10, -16, -15, 0, - -3, -3, -5, -3, 0, -3, -1, 6, - 0, 6, -3, 0, 12, 0, 0, 0, - -3, -4, -4, 0, 0, -10, 0, -2, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -4, -4, 0, -5, - 0, 4, -7, -7, -3, 0, -11, -3, - -8, -3, -5, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -7, 0, 0, 0, 0, -5, 0, -4, - 0, 0, -2, 0, -13, 3, 4, 4, - -1, -11, 3, 6, 3, 12, -10, 0, - -3, 0, -3, -15, 0, 0, -12, -10, - 0, -7, 0, -6, 0, -6, 0, -3, - 6, 0, -3, -12, -4, 14, 0, 0, - -4, 3, 0, 0, -13, 0, -3, -1, - 0, 0, 0, -3, 0, -3, -16, -5, - -8, 0, -12, 0, -4, 0, -7, 0, - 2, 0, -4, 0, -4, -12, 0, -4, - 4, 0, 1, 0, -5, -3, 0, -5, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -3, 0, 0, 0, 0, 1, 0, - -4, -4, 0, 0, 8, -24, 1, 17, - 12, 7, -15, 3, 16, 0, 14, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0 -}; - - -/*Collect the kern class' data in one place*/ -static const lv_font_fmt_txt_kern_classes_t kern_classes = -{ - .class_pair_values = kern_class_values, - .left_class_mapping = kern_left_class_mapping, - .right_class_mapping = kern_right_class_mapping, - .left_class_cnt = 45, - .right_class_cnt = 35, -}; - -/*-------------------- - * ALL CUSTOM DATA - *--------------------*/ - -#if LVGL_VERSION_MAJOR == 8 -/*Store all the custom data of the font*/ -static lv_font_fmt_txt_glyph_cache_t cache; -#endif - -#if LVGL_VERSION_MAJOR >= 8 -static const lv_font_fmt_txt_dsc_t font_dsc = { -#else -static lv_font_fmt_txt_dsc_t font_dsc = { -#endif - .glyph_bitmap = glyph_bitmap, - .glyph_dsc = glyph_dsc, - .cmaps = cmaps, - .kern_dsc = &kern_classes, - .kern_scale = 16, - .cmap_num = 5, - .bpp = 4, - .kern_classes = 1, - .bitmap_format = 0, -#if LVGL_VERSION_MAJOR == 8 - .cache = &cache -#endif -}; - - - -/*----------------- - * PUBLIC FONT - *----------------*/ - -/*Initialize a public general font descriptor*/ -#if LVGL_VERSION_MAJOR >= 8 -const lv_font_t montserrat_medium_24 = { -#else -lv_font_t montserrat_medium_24 = { -#endif - .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ - .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ - .line_height = 27, /*The maximum line height required by the font*/ - .base_line = 5, /*Baseline measured from the bottom of the line*/ -#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) - .subpx = LV_FONT_SUBPX_NONE, -#endif -#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 - .underline_position = -2, - .underline_thickness = 1, -#endif - .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ -#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 - .fallback = NULL, -#endif - .user_data = NULL, -}; - - - -#endif /*#if MONTSERRAT_MEDIUM_24*/ - +/******************************************************************************* + * Size: 24 px + * Bpp: 4 + * Opts: --bpp 4 --size 24 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°éûCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz %,' --format lvgl -o montserrat_medium_24.c --font fa-solid-900.ttf --range 61461,0xf0c2,0xf575 + ******************************************************************************/ + +#ifdef LV_LVGL_H_INCLUDE_SIMPLE +#include "lvgl.h" +#else +#include "lvgl/lvgl.h" +#endif + +#ifndef MONTSERRAT_MEDIUM_24 +#define MONTSERRAT_MEDIUM_24 1 +#endif + +#if MONTSERRAT_MEDIUM_24 + +/*----------------- + * BITMAPS + *----------------*/ + +/*Store the image of the glyphs*/ +static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { + /* U+0020 " " */ + + /* U+0025 "%" */ + 0x0, 0x3c, 0xfe, 0x90, 0x0, 0x0, 0x0, 0x6f, + 0x70, 0x0, 0x3, 0xfd, 0x78, 0xfb, 0x0, 0x0, + 0x2, 0xfc, 0x0, 0x0, 0xb, 0xe1, 0x0, 0x6f, + 0x40, 0x0, 0xc, 0xf2, 0x0, 0x0, 0xf, 0x90, + 0x0, 0xf, 0x90, 0x0, 0x7f, 0x60, 0x0, 0x0, + 0x1f, 0x70, 0x0, 0xe, 0xa0, 0x2, 0xfb, 0x0, + 0x0, 0x0, 0xf, 0x80, 0x0, 0xf, 0x90, 0xc, + 0xf1, 0x0, 0x0, 0x0, 0xd, 0xd0, 0x0, 0x3f, + 0x60, 0x7f, 0x60, 0x0, 0x0, 0x0, 0x5, 0xf9, + 0x24, 0xde, 0x2, 0xfb, 0x0, 0x1, 0x0, 0x0, + 0x0, 0x7f, 0xff, 0xd3, 0xc, 0xe1, 0x8, 0xff, + 0xe7, 0x0, 0x0, 0x1, 0x43, 0x0, 0x7f, 0x50, + 0x9f, 0x85, 0xaf, 0x70, 0x0, 0x0, 0x0, 0x2, + 0xfa, 0x2, 0xf8, 0x0, 0xb, 0xf0, 0x0, 0x0, + 0x0, 0xd, 0xe1, 0x5, 0xf3, 0x0, 0x5, 0xf4, + 0x0, 0x0, 0x0, 0x8f, 0x50, 0x6, 0xf1, 0x0, + 0x3, 0xf5, 0x0, 0x0, 0x3, 0xfa, 0x0, 0x5, + 0xf3, 0x0, 0x5, 0xf3, 0x0, 0x0, 0xd, 0xe1, + 0x0, 0x1, 0xf8, 0x0, 0xa, 0xe0, 0x0, 0x0, + 0x8f, 0x40, 0x0, 0x0, 0x8f, 0x84, 0x9f, 0x60, + 0x0, 0x3, 0xfa, 0x0, 0x0, 0x0, 0x7, 0xdf, + 0xd6, 0x0, + + /* U+0027 "'" */ + 0x7f, 0x87, 0xf7, 0x6f, 0x76, 0xf7, 0x6f, 0x65, + 0xf6, 0x38, 0x30, + + /* U+002C "," */ + 0x3b, 0x80, 0xcf, 0xf3, 0xaf, 0xf3, 0xf, 0xe0, + 0x1f, 0x90, 0x5f, 0x40, 0x9e, 0x0, + + /* U+002E "." */ + 0x4, 0x10, 0x9f, 0xf1, 0xdf, 0xf4, 0x6f, 0xb0, + + /* U+0030 "0" */ + 0x0, 0x1, 0x8d, 0xff, 0xd8, 0x10, 0x0, 0x0, + 0x2e, 0xff, 0xff, 0xff, 0xe2, 0x0, 0x1, 0xff, + 0xe7, 0x33, 0x7e, 0xff, 0x10, 0xb, 0xfe, 0x20, + 0x0, 0x2, 0xef, 0xb0, 0x2f, 0xf5, 0x0, 0x0, + 0x0, 0x5f, 0xf2, 0x7f, 0xe0, 0x0, 0x0, 0x0, + 0xe, 0xf7, 0xaf, 0xb0, 0x0, 0x0, 0x0, 0xb, + 0xfa, 0xcf, 0x90, 0x0, 0x0, 0x0, 0x9, 0xfc, + 0xdf, 0x80, 0x0, 0x0, 0x0, 0x8, 0xfd, 0xcf, + 0x90, 0x0, 0x0, 0x0, 0x9, 0xfc, 0xaf, 0xb0, + 0x0, 0x0, 0x0, 0xb, 0xfa, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0xe, 0xf7, 0x2f, 0xf5, 0x0, 0x0, + 0x0, 0x5f, 0xf2, 0xb, 0xfe, 0x10, 0x0, 0x2, + 0xef, 0xb0, 0x1, 0xff, 0xe7, 0x33, 0x7e, 0xff, + 0x10, 0x0, 0x3e, 0xff, 0xff, 0xff, 0xe2, 0x0, + 0x0, 0x1, 0x7c, 0xee, 0xc7, 0x10, 0x0, + + /* U+0031 "1" */ + 0xdf, 0xff, 0xff, 0x5d, 0xff, 0xff, 0xf5, 0x11, + 0x11, 0xff, 0x50, 0x0, 0xf, 0xf5, 0x0, 0x0, + 0xff, 0x50, 0x0, 0xf, 0xf5, 0x0, 0x0, 0xff, + 0x50, 0x0, 0xf, 0xf5, 0x0, 0x0, 0xff, 0x50, + 0x0, 0xf, 0xf5, 0x0, 0x0, 0xff, 0x50, 0x0, + 0xf, 0xf5, 0x0, 0x0, 0xff, 0x50, 0x0, 0xf, + 0xf5, 0x0, 0x0, 0xff, 0x50, 0x0, 0xf, 0xf5, + 0x0, 0x0, 0xff, 0x50, + + /* U+0032 "2" */ + 0x0, 0x17, 0xce, 0xfe, 0xc6, 0x0, 0x0, 0x7f, + 0xff, 0xff, 0xff, 0xfc, 0x10, 0x6f, 0xfc, 0x63, + 0x35, 0xbf, 0xfa, 0x0, 0x97, 0x0, 0x0, 0x0, + 0xaf, 0xf1, 0x0, 0x0, 0x0, 0x0, 0x3, 0xff, + 0x30, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xf2, 0x0, + 0x0, 0x0, 0x0, 0x8, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x2, 0xff, 0x70, 0x0, 0x0, 0x0, 0x2, + 0xef, 0xc0, 0x0, 0x0, 0x0, 0x2, 0xef, 0xd1, + 0x0, 0x0, 0x0, 0x2, 0xef, 0xd1, 0x0, 0x0, + 0x0, 0x3, 0xef, 0xc1, 0x0, 0x0, 0x0, 0x3, + 0xef, 0xc0, 0x0, 0x0, 0x0, 0x3, 0xff, 0xb0, + 0x0, 0x0, 0x0, 0x4, 0xff, 0xc2, 0x11, 0x11, + 0x11, 0x11, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, + + /* U+0033 "3" */ + 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xe0, 0x1, 0x11, 0x11, + 0x11, 0x7f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x3f, + 0xf7, 0x0, 0x0, 0x0, 0x0, 0x1e, 0xfa, 0x0, + 0x0, 0x0, 0x0, 0xc, 0xfd, 0x0, 0x0, 0x0, + 0x0, 0x9, 0xfe, 0x20, 0x0, 0x0, 0x0, 0x3, + 0xff, 0xfc, 0x71, 0x0, 0x0, 0x0, 0x3f, 0xff, + 0xff, 0xe3, 0x0, 0x0, 0x0, 0x0, 0x15, 0xef, + 0xe1, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x60, + 0x0, 0x0, 0x0, 0x0, 0xc, 0xf9, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xdf, 0x81, 0xa1, 0x0, 0x0, + 0x0, 0x4f, 0xf5, 0x9f, 0xfa, 0x53, 0x34, 0x9f, + 0xfd, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfd, 0x20, + 0x0, 0x49, 0xdf, 0xfe, 0xb6, 0x0, 0x0, + + /* U+0034 "4" */ + 0x0, 0x0, 0x0, 0x0, 0xd, 0xfb, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xaf, 0xe1, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6, 0xff, 0x30, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x3f, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xdf, 0xb0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xa, 0xfd, 0x10, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xf3, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x3, 0xff, 0x60, 0x0, 0x9d, 0x70, 0x0, + 0x0, 0x1e, 0xfa, 0x0, 0x0, 0xbf, 0x90, 0x0, + 0x0, 0xbf, 0xd0, 0x0, 0x0, 0xbf, 0x90, 0x0, + 0x7, 0xff, 0x41, 0x11, 0x11, 0xbf, 0x91, 0x11, + 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, + 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x90, 0x0, + + /* U+0035 "5" */ + 0x0, 0x8f, 0xff, 0xff, 0xff, 0xff, 0x0, 0xa, + 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0, 0xbf, 0x81, + 0x11, 0x11, 0x11, 0x0, 0xd, 0xf6, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xef, 0x40, 0x0, 0x0, 0x0, + 0x0, 0xf, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x2, + 0xff, 0x31, 0x10, 0x0, 0x0, 0x0, 0x3f, 0xff, + 0xff, 0xfe, 0xa3, 0x0, 0x5, 0xff, 0xff, 0xff, + 0xff, 0xf8, 0x0, 0x0, 0x0, 0x0, 0x26, 0xdf, + 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0xb0, + 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x8f, 0xd0, 0x93, 0x0, 0x0, + 0x0, 0x1e, 0xfa, 0x5f, 0xfb, 0x63, 0x24, 0x7e, + 0xff, 0x31, 0xbf, 0xff, 0xff, 0xff, 0xff, 0x50, + 0x0, 0x28, 0xce, 0xfe, 0xc8, 0x10, 0x0, + + /* U+0036 "6" */ + 0x0, 0x0, 0x4a, 0xdf, 0xfe, 0xb5, 0x0, 0x0, + 0xa, 0xff, 0xff, 0xff, 0xff, 0x10, 0x0, 0xcf, + 0xf9, 0x42, 0x23, 0x76, 0x0, 0x8, 0xfe, 0x30, + 0x0, 0x0, 0x0, 0x0, 0xf, 0xf5, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6f, 0xe0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xaf, 0xa0, 0x5b, 0xef, 0xd9, 0x30, + 0x0, 0xbf, 0x9a, 0xff, 0xff, 0xff, 0xf7, 0x0, + 0xdf, 0xff, 0xc4, 0x1, 0x4c, 0xff, 0x40, 0xcf, + 0xfc, 0x0, 0x0, 0x0, 0xcf, 0xc0, 0xbf, 0xf5, + 0x0, 0x0, 0x0, 0x5f, 0xf0, 0x8f, 0xf2, 0x0, + 0x0, 0x0, 0x3f, 0xf1, 0x4f, 0xf4, 0x0, 0x0, + 0x0, 0x4f, 0xf0, 0xd, 0xfc, 0x0, 0x0, 0x0, + 0xbf, 0xb0, 0x4, 0xff, 0xc3, 0x0, 0x3b, 0xff, + 0x30, 0x0, 0x5f, 0xff, 0xff, 0xff, 0xf5, 0x0, + 0x0, 0x1, 0x8d, 0xff, 0xd9, 0x20, 0x0, + + /* U+0037 "7" */ + 0x4f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf6, 0x4f, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xf5, 0x4f, 0xf2, + 0x11, 0x11, 0x11, 0x8f, 0xf1, 0x4f, 0xf0, 0x0, + 0x0, 0x0, 0xef, 0x90, 0x4f, 0xf0, 0x0, 0x0, + 0x5, 0xff, 0x20, 0x2, 0x20, 0x0, 0x0, 0xc, + 0xfa, 0x0, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf3, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xbf, 0xc0, 0x0, + 0x0, 0x0, 0x0, 0x2, 0xff, 0x50, 0x0, 0x0, + 0x0, 0x0, 0x9, 0xfe, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x1f, 0xf7, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x7f, 0xf1, 0x0, 0x0, 0x0, 0x0, 0x0, 0xef, + 0x90, 0x0, 0x0, 0x0, 0x0, 0x6, 0xff, 0x20, + 0x0, 0x0, 0x0, 0x0, 0xd, 0xfb, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x4f, 0xf4, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xbf, 0xd0, 0x0, 0x0, 0x0, + + /* U+0038 "8" */ + 0x0, 0x6, 0xbe, 0xff, 0xd9, 0x20, 0x0, 0x2, + 0xdf, 0xff, 0xff, 0xff, 0xf7, 0x0, 0xd, 0xff, + 0x71, 0x0, 0x4b, 0xff, 0x40, 0x3f, 0xf5, 0x0, + 0x0, 0x0, 0xcf, 0xa0, 0x4f, 0xf1, 0x0, 0x0, + 0x0, 0x9f, 0xc0, 0x2f, 0xf5, 0x0, 0x0, 0x0, + 0xdf, 0x90, 0xa, 0xff, 0x72, 0x1, 0x4c, 0xff, + 0x20, 0x0, 0x8f, 0xff, 0xff, 0xff, 0xd3, 0x0, + 0x4, 0xdf, 0xff, 0xef, 0xff, 0xf8, 0x0, 0x2f, + 0xfc, 0x40, 0x0, 0x18, 0xff, 0x90, 0xaf, 0xd0, + 0x0, 0x0, 0x0, 0x6f, 0xf2, 0xdf, 0x80, 0x0, + 0x0, 0x0, 0xf, 0xf5, 0xdf, 0x80, 0x0, 0x0, + 0x0, 0x1f, 0xf5, 0xaf, 0xe1, 0x0, 0x0, 0x0, + 0x8f, 0xf2, 0x3f, 0xfd, 0x51, 0x0, 0x3a, 0xff, + 0xa0, 0x5, 0xff, 0xff, 0xff, 0xff, 0xfa, 0x0, + 0x0, 0x17, 0xce, 0xff, 0xd9, 0x40, 0x0, + + /* U+0039 "9" */ + 0x0, 0x4, 0xae, 0xfe, 0xc7, 0x0, 0x0, 0x0, + 0xaf, 0xff, 0xff, 0xff, 0xe2, 0x0, 0x8, 0xff, + 0x82, 0x0, 0x4c, 0xfe, 0x10, 0x1f, 0xf6, 0x0, + 0x0, 0x0, 0xcf, 0xa0, 0x3f, 0xf0, 0x0, 0x0, + 0x0, 0x6f, 0xf1, 0x4f, 0xf0, 0x0, 0x0, 0x0, + 0x6f, 0xf5, 0x1f, 0xf6, 0x0, 0x0, 0x0, 0xcf, + 0xf8, 0xa, 0xff, 0x82, 0x0, 0x4c, 0xff, 0xf9, + 0x0, 0xcf, 0xff, 0xff, 0xff, 0x9c, 0xfa, 0x0, + 0x6, 0xbe, 0xfe, 0xa4, 0xd, 0xf8, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xf, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x3f, 0xf2, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xbf, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x8, + 0xff, 0x50, 0x0, 0xa7, 0x31, 0x25, 0xcf, 0xf9, + 0x0, 0x3, 0xff, 0xff, 0xff, 0xff, 0x80, 0x0, + 0x0, 0x7b, 0xdf, 0xec, 0x82, 0x0, 0x0, + + /* U+0041 "A" */ + 0x0, 0x0, 0x0, 0x0, 0xaf, 0xf2, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0xa0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, + 0xff, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xff, 0x5d, 0xf8, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7f, 0xe0, 0x6f, 0xe0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xd, 0xf7, 0x0, 0xef, 0x60, 0x0, + 0x0, 0x0, 0x0, 0x5, 0xff, 0x10, 0x8, 0xfd, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0xa0, 0x0, + 0x1f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xf3, + 0x0, 0x0, 0xaf, 0xc0, 0x0, 0x0, 0x0, 0xa, + 0xfc, 0x0, 0x0, 0x4, 0xff, 0x30, 0x0, 0x0, + 0x2, 0xff, 0x50, 0x0, 0x0, 0xd, 0xfa, 0x0, + 0x0, 0x0, 0x9f, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf2, 0x0, 0x0, 0x1f, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x90, 0x0, 0x7, 0xff, 0x10, 0x0, + 0x0, 0x0, 0x8, 0xff, 0x10, 0x0, 0xef, 0x90, + 0x0, 0x0, 0x0, 0x0, 0x1f, 0xf7, 0x0, 0x5f, + 0xf2, 0x0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe0, + 0xc, 0xfa, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, + 0xff, 0x50, + + /* U+0042 "B" */ + 0x7f, 0xff, 0xff, 0xff, 0xfe, 0xb6, 0x0, 0x7, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xfd, 0x10, 0x7f, + 0xe0, 0x0, 0x0, 0x2, 0x9f, 0xfa, 0x7, 0xfe, + 0x0, 0x0, 0x0, 0x0, 0x9f, 0xf0, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x5, 0xff, 0x7, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x9f, 0xd0, 0x7f, 0xe0, 0x0, + 0x0, 0x2, 0x9f, 0xf5, 0x7, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf6, 0x0, 0x7f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xd4, 0x7, 0xfe, 0x0, 0x0, 0x0, + 0x14, 0xcf, 0xf3, 0x7f, 0xe0, 0x0, 0x0, 0x0, + 0x0, 0xdf, 0xa7, 0xfe, 0x0, 0x0, 0x0, 0x0, + 0x8, 0xfd, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x8f, 0xe7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0xc, + 0xfc, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x3b, 0xff, + 0x67, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x90, + 0x7f, 0xff, 0xff, 0xff, 0xff, 0xd9, 0x30, 0x0, + + /* U+0043 "C" */ + 0x0, 0x0, 0x5, 0xad, 0xff, 0xda, 0x50, 0x0, + 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfd, 0x30, + 0x0, 0x5f, 0xff, 0xb6, 0x43, 0x59, 0xff, 0xf2, + 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0x1c, 0x80, + 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x5f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xdf, 0x90, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x9f, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x5f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0x1c, 0x80, + 0x0, 0x5f, 0xff, 0xb5, 0x33, 0x49, 0xff, 0xf2, + 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfd, 0x30, + 0x0, 0x0, 0x5, 0xae, 0xff, 0xda, 0x50, 0x0, + + /* U+0044 "D" */ + 0x7f, 0xff, 0xff, 0xff, 0xfd, 0x94, 0x0, 0x0, + 0x7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x20, + 0x0, 0x7f, 0xe1, 0x11, 0x12, 0x36, 0xbf, 0xff, + 0x40, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x4e, + 0xfe, 0x20, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x2f, 0xfb, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7f, 0xf2, 0x7f, 0xe0, 0x0, 0x0, 0x0, + 0x0, 0x1, 0xff, 0x77, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xd, 0xf9, 0x7f, 0xe0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xcf, 0xa7, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xd, 0xf9, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0x0, 0x1, 0xff, 0x77, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf2, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x0, 0x2f, 0xfb, 0x7, 0xfe, + 0x0, 0x0, 0x0, 0x0, 0x3e, 0xfe, 0x20, 0x7f, + 0xe1, 0x11, 0x11, 0x35, 0xbf, 0xff, 0x40, 0x7, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x20, 0x0, + 0x7f, 0xff, 0xff, 0xff, 0xfd, 0x94, 0x0, 0x0, + 0x0, + + /* U+0045 "E" */ + 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x67, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf6, 0x7f, 0xe1, 0x11, + 0x11, 0x11, 0x11, 0x7, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, + 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0xff, + 0xff, 0xff, 0xff, 0x50, 0x7f, 0xff, 0xff, 0xff, + 0xff, 0xf5, 0x7, 0xfe, 0x11, 0x11, 0x11, 0x11, + 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, + 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x7f, 0xe1, 0x11, 0x11, 0x11, + 0x11, 0x17, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfb, + 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xb0, + + /* U+0046 "F" */ + 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x67, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf6, 0x7f, 0xe1, 0x11, + 0x11, 0x11, 0x11, 0x7, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, + 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x7f, 0xff, 0xff, 0xff, + 0xff, 0xf5, 0x7, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x50, 0x7f, 0xe1, 0x11, 0x11, 0x11, 0x10, 0x7, + 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, + 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, + + /* U+0047 "G" */ + 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, + 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xfe, 0x50, + 0x0, 0x5f, 0xff, 0xb6, 0x43, 0x48, 0xef, 0xf5, + 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0x9, 0xb0, + 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x5f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xdf, 0x90, 0x0, 0x0, 0x0, 0x0, 0x7, 0x94, + 0xcf, 0xa0, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x5f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x3, 0xff, 0xd3, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x0, 0x5f, 0xff, 0xb6, 0x32, 0x47, 0xdf, 0xf7, + 0x0, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xff, 0x80, + 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x71, 0x0, + + /* U+0048 "H" */ + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, + 0xfe, 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, + 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xfe, + 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf7, 0xfe, 0x11, 0x11, 0x11, + 0x11, 0x17, 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, + 0x0, 0x7f, 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, + 0x7, 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x7f, 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x7, + 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, + 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf0, + + /* U+0049 "I" */ + 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, + 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, + 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, 0x7f, 0xe7, 0xfe, + 0x7f, 0xe0, + + /* U+004A "J" */ + 0x0, 0x8f, 0xff, 0xff, 0xff, 0xf0, 0x8, 0xff, + 0xff, 0xff, 0xff, 0x0, 0x1, 0x11, 0x11, 0x7f, + 0xf0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xf0, 0x0, 0x0, 0x0, 0x7, + 0xff, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf0, 0x0, + 0x0, 0x0, 0x7, 0xff, 0x0, 0x0, 0x0, 0x0, + 0x7f, 0xf0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x0, + 0x0, 0x0, 0x0, 0x7f, 0xf0, 0x0, 0x0, 0x0, + 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xd0, + 0x5a, 0x0, 0x0, 0xd, 0xfa, 0xf, 0xfc, 0x41, + 0x3b, 0xff, 0x50, 0x5f, 0xff, 0xff, 0xff, 0xa0, + 0x0, 0x29, 0xdf, 0xfc, 0x60, 0x0, + + /* U+004B "K" */ + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x6, 0xff, 0x50, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x6f, 0xf6, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x5, 0xff, 0x60, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x5f, 0xf7, 0x0, 0x0, + 0x7f, 0xe0, 0x0, 0x4, 0xff, 0x80, 0x0, 0x0, + 0x7f, 0xe0, 0x0, 0x4f, 0xf9, 0x0, 0x0, 0x0, + 0x7f, 0xe0, 0x3, 0xff, 0xa0, 0x0, 0x0, 0x0, + 0x7f, 0xe0, 0x3f, 0xfd, 0x0, 0x0, 0x0, 0x0, + 0x7f, 0xe2, 0xef, 0xff, 0x40, 0x0, 0x0, 0x0, + 0x7f, 0xfe, 0xfd, 0xdf, 0xf2, 0x0, 0x0, 0x0, + 0x7f, 0xff, 0xd1, 0x2f, 0xfd, 0x10, 0x0, 0x0, + 0x7f, 0xfe, 0x10, 0x4, 0xff, 0xb0, 0x0, 0x0, + 0x7f, 0xf2, 0x0, 0x0, 0x6f, 0xf8, 0x0, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x8, 0xff, 0x50, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0xbf, 0xf3, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0xc, 0xfe, 0x10, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x1, 0xef, 0xc0, + + /* U+004C "L" */ + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, + 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, + 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x7, + 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x0, 0x7, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x7f, 0xe1, 0x11, 0x11, 0x11, + 0x11, 0x7, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, + 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0, + + /* U+004D "M" */ + 0x7f, 0xc0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xdf, 0x57, 0xff, 0x50, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7f, 0xf6, 0x7f, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x1f, 0xff, 0x67, 0xff, 0xf8, 0x0, + 0x0, 0x0, 0x0, 0x9, 0xff, 0xf6, 0x7f, 0xff, + 0xf2, 0x0, 0x0, 0x0, 0x3, 0xff, 0xff, 0x67, + 0xfd, 0xbf, 0xb0, 0x0, 0x0, 0x0, 0xcf, 0x8e, + 0xf6, 0x7f, 0xd2, 0xff, 0x40, 0x0, 0x0, 0x5f, + 0xe0, 0xef, 0x67, 0xfd, 0x8, 0xfd, 0x0, 0x0, + 0xe, 0xf6, 0xe, 0xf6, 0x7f, 0xd0, 0xe, 0xf7, + 0x0, 0x8, 0xfc, 0x0, 0xef, 0x67, 0xfd, 0x0, + 0x5f, 0xf1, 0x1, 0xff, 0x30, 0xe, 0xf6, 0x7f, + 0xd0, 0x0, 0xbf, 0xa0, 0xaf, 0x90, 0x0, 0xef, + 0x67, 0xfd, 0x0, 0x2, 0xff, 0x7f, 0xe1, 0x0, + 0xe, 0xf6, 0x7f, 0xd0, 0x0, 0x8, 0xff, 0xf6, + 0x0, 0x0, 0xef, 0x67, 0xfd, 0x0, 0x0, 0xe, + 0xfd, 0x0, 0x0, 0xe, 0xf6, 0x7f, 0xd0, 0x0, + 0x0, 0x5f, 0x40, 0x0, 0x0, 0xef, 0x67, 0xfd, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xe, 0xf6, + 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xef, 0x60, + + /* U+004E "N" */ + 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x0, 0x7f, 0xf7, + 0xff, 0xa0, 0x0, 0x0, 0x0, 0x7, 0xff, 0x7f, + 0xff, 0x70, 0x0, 0x0, 0x0, 0x7f, 0xf7, 0xff, + 0xff, 0x40, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xfd, + 0xfe, 0x20, 0x0, 0x0, 0x7f, 0xf7, 0xfe, 0x3f, + 0xfd, 0x0, 0x0, 0x7, 0xff, 0x7f, 0xe0, 0x5f, + 0xfa, 0x0, 0x0, 0x7f, 0xf7, 0xfe, 0x0, 0x8f, + 0xf7, 0x0, 0x7, 0xff, 0x7f, 0xe0, 0x0, 0xbf, + 0xf4, 0x0, 0x7f, 0xf7, 0xfe, 0x0, 0x1, 0xef, + 0xe1, 0x7, 0xff, 0x7f, 0xe0, 0x0, 0x3, 0xff, + 0xc0, 0x7f, 0xf7, 0xfe, 0x0, 0x0, 0x6, 0xff, + 0xa7, 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x9, 0xff, + 0xdf, 0xf7, 0xfe, 0x0, 0x0, 0x0, 0xc, 0xff, + 0xff, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x1e, 0xff, + 0xf7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x3f, 0xff, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x6f, 0xf0, + + /* U+004F "O" */ + 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, + 0x0, 0x0, 0x0, 0x2d, 0xff, 0xff, 0xff, 0xff, + 0xe4, 0x0, 0x0, 0x0, 0x5f, 0xff, 0xb6, 0x33, + 0x5a, 0xff, 0xf7, 0x0, 0x0, 0x3f, 0xfd, 0x30, + 0x0, 0x0, 0x1, 0xcf, 0xf5, 0x0, 0xd, 0xfe, + 0x10, 0x0, 0x0, 0x0, 0x0, 0xcf, 0xf1, 0x4, + 0xff, 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, + 0x70, 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xb, 0xfc, 0xc, 0xfa, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x8f, 0xf0, 0xdf, 0x90, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6, 0xff, 0xc, 0xfa, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xf0, 0x9f, + 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, 0xfc, + 0x5, 0xff, 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, + 0xff, 0x70, 0xd, 0xfe, 0x10, 0x0, 0x0, 0x0, + 0x0, 0xcf, 0xf1, 0x0, 0x3f, 0xfd, 0x30, 0x0, + 0x0, 0x1, 0xcf, 0xf5, 0x0, 0x0, 0x5f, 0xff, + 0xb5, 0x33, 0x59, 0xff, 0xf8, 0x0, 0x0, 0x0, + 0x3d, 0xff, 0xff, 0xff, 0xff, 0xe4, 0x0, 0x0, + 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, + 0x0, 0x0, + + /* U+0050 "P" */ + 0x7f, 0xff, 0xff, 0xff, 0xeb, 0x60, 0x0, 0x7, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xd2, 0x0, 0x7f, + 0xe1, 0x11, 0x12, 0x49, 0xff, 0xe1, 0x7, 0xfe, + 0x0, 0x0, 0x0, 0x3, 0xff, 0x90, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x9, 0xfe, 0x7, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x5f, 0xf0, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0x5, 0xff, 0x7, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x9f, 0xe0, 0x7f, 0xe0, 0x0, 0x0, + 0x0, 0x3f, 0xf9, 0x7, 0xfe, 0x11, 0x11, 0x24, + 0x8f, 0xfe, 0x10, 0x7f, 0xff, 0xff, 0xff, 0xff, + 0xfd, 0x20, 0x7, 0xff, 0xff, 0xff, 0xfe, 0xb6, + 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x7, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + + /* U+0051 "Q" */ + 0x0, 0x0, 0x5, 0xad, 0xff, 0xeb, 0x60, 0x0, + 0x0, 0x0, 0x0, 0x2d, 0xff, 0xff, 0xff, 0xff, + 0xe4, 0x0, 0x0, 0x0, 0x5f, 0xff, 0xb6, 0x33, + 0x5a, 0xff, 0xf7, 0x0, 0x0, 0x2f, 0xfd, 0x30, + 0x0, 0x0, 0x2, 0xcf, 0xf5, 0x0, 0xd, 0xfe, + 0x10, 0x0, 0x0, 0x0, 0x0, 0xdf, 0xf1, 0x4, + 0xff, 0x50, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, + 0x70, 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xb, 0xfc, 0xc, 0xfa, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x8f, 0xf0, 0xdf, 0x90, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6, 0xff, 0xc, 0xfa, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x8f, 0xe0, 0xaf, + 0xd0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, 0xfc, + 0x5, 0xff, 0x40, 0x0, 0x0, 0x0, 0x0, 0x2, + 0xff, 0x70, 0xe, 0xfd, 0x10, 0x0, 0x0, 0x0, + 0x0, 0xcf, 0xf1, 0x0, 0x4f, 0xfd, 0x20, 0x0, + 0x0, 0x1, 0xbf, 0xf6, 0x0, 0x0, 0x7f, 0xff, + 0xa4, 0x22, 0x48, 0xef, 0xf9, 0x0, 0x0, 0x0, + 0x5f, 0xff, 0xff, 0xff, 0xff, 0xf6, 0x0, 0x0, + 0x0, 0x0, 0x17, 0xce, 0xff, 0xfd, 0x71, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x1, 0xcf, 0xf7, + 0x10, 0x4, 0xc3, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x9f, 0xff, 0xff, 0xff, 0x70, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x3a, 0xef, 0xea, 0x40, + + /* U+0052 "R" */ + 0x7f, 0xff, 0xff, 0xff, 0xeb, 0x60, 0x0, 0x7, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xd2, 0x0, 0x7f, + 0xe1, 0x11, 0x12, 0x49, 0xff, 0xe1, 0x7, 0xfe, + 0x0, 0x0, 0x0, 0x3, 0xff, 0x90, 0x7f, 0xe0, + 0x0, 0x0, 0x0, 0x9, 0xfe, 0x7, 0xfe, 0x0, + 0x0, 0x0, 0x0, 0x5f, 0xf0, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0x5, 0xff, 0x7, 0xfe, 0x0, 0x0, + 0x0, 0x0, 0x9f, 0xe0, 0x7f, 0xe0, 0x0, 0x0, + 0x0, 0x3f, 0xf8, 0x7, 0xfe, 0x11, 0x11, 0x13, + 0x8f, 0xfe, 0x10, 0x7f, 0xff, 0xff, 0xff, 0xff, + 0xfd, 0x20, 0x7, 0xff, 0xff, 0xff, 0xff, 0xfa, + 0x0, 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x7f, 0xf2, + 0x0, 0x7, 0xfe, 0x0, 0x0, 0x0, 0xcf, 0xd0, + 0x0, 0x7f, 0xe0, 0x0, 0x0, 0x1, 0xef, 0x90, + 0x7, 0xfe, 0x0, 0x0, 0x0, 0x5, 0xff, 0x40, + 0x7f, 0xe0, 0x0, 0x0, 0x0, 0x9, 0xfe, 0x10, + + /* U+0053 "S" */ + 0x0, 0x0, 0x6b, 0xef, 0xfd, 0xa5, 0x0, 0x0, + 0x2e, 0xff, 0xff, 0xff, 0xff, 0xd1, 0x0, 0xef, + 0xe7, 0x21, 0x14, 0x8e, 0xc0, 0x6, 0xff, 0x20, + 0x0, 0x0, 0x0, 0x20, 0x9, 0xfc, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x8, 0xfe, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x3, 0xff, 0xc3, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x7f, 0xff, 0xd9, 0x51, 0x0, 0x0, + 0x0, 0x4, 0xbf, 0xff, 0xff, 0xc5, 0x0, 0x0, + 0x0, 0x1, 0x59, 0xdf, 0xff, 0xb0, 0x0, 0x0, + 0x0, 0x0, 0x2, 0xaf, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xb, 0xfc, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x7, 0xfe, 0x5, 0x80, 0x0, 0x0, 0x0, + 0xc, 0xfb, 0xd, 0xfe, 0x84, 0x21, 0x25, 0xcf, + 0xf4, 0x3, 0xdf, 0xff, 0xff, 0xff, 0xff, 0x60, + 0x0, 0x4, 0x9d, 0xef, 0xec, 0x82, 0x0, + + /* U+0054 "T" */ + 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x11, 0x11, + 0x13, 0xff, 0x51, 0x11, 0x11, 0x0, 0x0, 0x2, + 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, + 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, + 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, + 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, + 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, 0x0, + 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, + 0x2, 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, + 0xff, 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, + 0x30, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, + 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, + 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, + 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, + + /* U+0055 "U" */ + 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x9a, + 0xfc, 0x0, 0x0, 0x0, 0x0, 0xc, 0xf9, 0xaf, + 0xc0, 0x0, 0x0, 0x0, 0x0, 0xcf, 0x9a, 0xfc, + 0x0, 0x0, 0x0, 0x0, 0xc, 0xf9, 0xaf, 0xc0, + 0x0, 0x0, 0x0, 0x0, 0xcf, 0x9a, 0xfc, 0x0, + 0x0, 0x0, 0x0, 0xc, 0xf9, 0xaf, 0xc0, 0x0, + 0x0, 0x0, 0x0, 0xcf, 0x9a, 0xfc, 0x0, 0x0, + 0x0, 0x0, 0xc, 0xf9, 0xaf, 0xc0, 0x0, 0x0, + 0x0, 0x0, 0xcf, 0x99, 0xfc, 0x0, 0x0, 0x0, + 0x0, 0xc, 0xf9, 0x9f, 0xd0, 0x0, 0x0, 0x0, + 0x0, 0xdf, 0x87, 0xff, 0x0, 0x0, 0x0, 0x0, + 0xf, 0xf6, 0x3f, 0xf5, 0x0, 0x0, 0x0, 0x5, + 0xff, 0x20, 0xcf, 0xe1, 0x0, 0x0, 0x1, 0xef, + 0xc0, 0x3, 0xff, 0xe7, 0x32, 0x38, 0xef, 0xf3, + 0x0, 0x4, 0xff, 0xff, 0xff, 0xff, 0xe4, 0x0, + 0x0, 0x1, 0x7c, 0xef, 0xec, 0x71, 0x0, 0x0, + + /* U+0056 "V" */ + 0xd, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x8, + 0xfe, 0x0, 0x6f, 0xf3, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xef, 0x70, 0x0, 0xef, 0xa0, 0x0, 0x0, + 0x0, 0x0, 0x6f, 0xf1, 0x0, 0x8, 0xff, 0x10, + 0x0, 0x0, 0x0, 0xc, 0xf9, 0x0, 0x0, 0x1f, + 0xf8, 0x0, 0x0, 0x0, 0x4, 0xff, 0x20, 0x0, + 0x0, 0xaf, 0xe0, 0x0, 0x0, 0x0, 0xbf, 0xb0, + 0x0, 0x0, 0x3, 0xff, 0x50, 0x0, 0x0, 0x2f, + 0xf4, 0x0, 0x0, 0x0, 0xc, 0xfc, 0x0, 0x0, + 0x9, 0xfd, 0x0, 0x0, 0x0, 0x0, 0x5f, 0xf3, + 0x0, 0x0, 0xff, 0x60, 0x0, 0x0, 0x0, 0x0, + 0xef, 0xa0, 0x0, 0x7f, 0xf0, 0x0, 0x0, 0x0, + 0x0, 0x7, 0xff, 0x10, 0xd, 0xf8, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x1f, 0xf8, 0x5, 0xff, 0x20, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe0, 0xcf, + 0xb0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, + 0x9f, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xb, 0xff, 0xfd, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x4f, 0xff, 0x60, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xdf, 0xe0, 0x0, 0x0, + 0x0, 0x0, + + /* U+0057 "W" */ + 0x1f, 0xf6, 0x0, 0x0, 0x0, 0x0, 0xaf, 0xe0, + 0x0, 0x0, 0x0, 0x3, 0xff, 0x10, 0xbf, 0xb0, + 0x0, 0x0, 0x0, 0xf, 0xff, 0x30, 0x0, 0x0, + 0x0, 0x8f, 0xc0, 0x6, 0xff, 0x10, 0x0, 0x0, + 0x5, 0xff, 0xf8, 0x0, 0x0, 0x0, 0xd, 0xf6, + 0x0, 0x1f, 0xf6, 0x0, 0x0, 0x0, 0xbf, 0xef, + 0xe0, 0x0, 0x0, 0x3, 0xff, 0x10, 0x0, 0xbf, + 0xb0, 0x0, 0x0, 0x1f, 0xf4, 0xff, 0x30, 0x0, + 0x0, 0x8f, 0xc0, 0x0, 0x6, 0xff, 0x10, 0x0, + 0x6, 0xfd, 0xc, 0xf8, 0x0, 0x0, 0xd, 0xf6, + 0x0, 0x0, 0x1f, 0xf5, 0x0, 0x0, 0xbf, 0x70, + 0x6f, 0xe0, 0x0, 0x3, 0xff, 0x10, 0x0, 0x0, + 0xcf, 0xb0, 0x0, 0x1f, 0xf2, 0x1, 0xff, 0x30, + 0x0, 0x8f, 0xc0, 0x0, 0x0, 0x6, 0xff, 0x0, + 0x6, 0xfd, 0x0, 0xc, 0xf8, 0x0, 0xd, 0xf7, + 0x0, 0x0, 0x0, 0x1f, 0xf5, 0x0, 0xbf, 0x70, + 0x0, 0x6f, 0xe0, 0x3, 0xff, 0x10, 0x0, 0x0, + 0x0, 0xcf, 0xb0, 0x1f, 0xf2, 0x0, 0x1, 0xff, + 0x30, 0x8f, 0xc0, 0x0, 0x0, 0x0, 0x6, 0xff, + 0x6, 0xfc, 0x0, 0x0, 0xb, 0xf8, 0xd, 0xf7, + 0x0, 0x0, 0x0, 0x0, 0x1f, 0xf5, 0xcf, 0x70, + 0x0, 0x0, 0x6f, 0xe3, 0xff, 0x20, 0x0, 0x0, + 0x0, 0x0, 0xcf, 0xcf, 0xf2, 0x0, 0x0, 0x1, + 0xff, 0xbf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0x7, + 0xff, 0xfc, 0x0, 0x0, 0x0, 0xb, 0xff, 0xf7, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0x70, + 0x0, 0x0, 0x0, 0x6f, 0xff, 0x20, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xcf, 0xf1, 0x0, 0x0, 0x0, + 0x1, 0xff, 0xc0, 0x0, 0x0, 0x0, + + /* U+0058 "X" */ + 0x1e, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe1, + 0x3, 0xff, 0x80, 0x0, 0x0, 0x4, 0xff, 0x50, + 0x0, 0x8f, 0xf3, 0x0, 0x0, 0x1e, 0xf9, 0x0, + 0x0, 0xc, 0xfe, 0x10, 0x0, 0xbf, 0xd0, 0x0, + 0x0, 0x2, 0xff, 0xa0, 0x6, 0xff, 0x20, 0x0, + 0x0, 0x0, 0x5f, 0xf6, 0x2f, 0xf6, 0x0, 0x0, + 0x0, 0x0, 0xa, 0xff, 0xdf, 0xb0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xef, 0xfe, 0x10, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x9f, 0xfb, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x4, 0xff, 0xff, 0x60, 0x0, 0x0, + 0x0, 0x0, 0x1e, 0xfa, 0x9f, 0xf2, 0x0, 0x0, + 0x0, 0x0, 0xbf, 0xe1, 0xd, 0xfd, 0x0, 0x0, + 0x0, 0x6, 0xff, 0x40, 0x2, 0xff, 0x90, 0x0, + 0x0, 0x2f, 0xf8, 0x0, 0x0, 0x6f, 0xf5, 0x0, + 0x0, 0xdf, 0xd0, 0x0, 0x0, 0xb, 0xfe, 0x10, + 0x9, 0xff, 0x20, 0x0, 0x0, 0x1, 0xef, 0xb0, + 0x5f, 0xf6, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf7, + + /* U+0059 "Y" */ + 0xc, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x1, 0xff, + 0x50, 0x3f, 0xf5, 0x0, 0x0, 0x0, 0x0, 0xaf, + 0xb0, 0x0, 0x9f, 0xe0, 0x0, 0x0, 0x0, 0x4f, + 0xf2, 0x0, 0x1, 0xef, 0x90, 0x0, 0x0, 0xd, + 0xf8, 0x0, 0x0, 0x6, 0xff, 0x20, 0x0, 0x7, + 0xfe, 0x0, 0x0, 0x0, 0xc, 0xfc, 0x0, 0x1, + 0xff, 0x50, 0x0, 0x0, 0x0, 0x3f, 0xf5, 0x0, + 0xaf, 0xb0, 0x0, 0x0, 0x0, 0x0, 0x9f, 0xe0, + 0x4f, 0xf2, 0x0, 0x0, 0x0, 0x0, 0x1, 0xef, + 0x9d, 0xf8, 0x0, 0x0, 0x0, 0x0, 0x0, 0x6, + 0xff, 0xfe, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xc, 0xff, 0x50, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x6, 0xff, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x6, 0xff, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6f, 0xf0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x6, 0xff, 0x0, 0x0, 0x0, + 0x0, + + /* U+005A "Z" */ + 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xc, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xb0, 0x11, + 0x11, 0x11, 0x11, 0x11, 0xcf, 0xf2, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x8f, 0xf4, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x5f, 0xf8, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x2f, 0xfb, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xd, 0xfd, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, + 0xff, 0x20, 0x0, 0x0, 0x0, 0x0, 0x8, 0xff, + 0x50, 0x0, 0x0, 0x0, 0x0, 0x4, 0xff, 0x80, + 0x0, 0x0, 0x0, 0x0, 0x2, 0xff, 0xb0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xdf, 0xd1, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xbf, 0xf3, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x8f, 0xf5, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x4f, 0xfa, 0x11, 0x11, 0x11, 0x11, 0x11, + 0xe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf1, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x10, + + /* U+0061 "a" */ + 0x0, 0x6b, 0xef, 0xfd, 0x81, 0x0, 0x2e, 0xff, + 0xff, 0xff, 0xfe, 0x10, 0xe, 0xb5, 0x10, 0x27, + 0xff, 0xb0, 0x1, 0x0, 0x0, 0x0, 0x6f, 0xf0, + 0x0, 0x0, 0x0, 0x0, 0x1f, 0xf3, 0x0, 0x37, + 0xaa, 0xaa, 0xaf, 0xf4, 0xa, 0xff, 0xff, 0xff, + 0xff, 0xf4, 0x6f, 0xf6, 0x10, 0x0, 0xf, 0xf4, + 0xbf, 0x90, 0x0, 0x0, 0xf, 0xf4, 0xcf, 0x80, + 0x0, 0x0, 0x5f, 0xf4, 0x8f, 0xe2, 0x0, 0x4, + 0xff, 0xf4, 0x1d, 0xff, 0xcb, 0xdf, 0xdf, 0xf4, + 0x1, 0x8d, 0xff, 0xd8, 0xe, 0xf4, + + /* U+0062 "b" */ + 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, + 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, + 0x0, 0x0, 0x0, 0xdf, 0x70, 0x7c, 0xfe, 0xc7, + 0x10, 0x0, 0xdf, 0x9d, 0xff, 0xff, 0xff, 0xe3, + 0x0, 0xdf, 0xff, 0xa3, 0x12, 0x6e, 0xfe, 0x20, + 0xdf, 0xf8, 0x0, 0x0, 0x1, 0xef, 0xa0, 0xdf, + 0xe0, 0x0, 0x0, 0x0, 0x6f, 0xf1, 0xdf, 0x90, + 0x0, 0x0, 0x0, 0x1f, 0xf3, 0xdf, 0x70, 0x0, + 0x0, 0x0, 0xf, 0xf5, 0xdf, 0x90, 0x0, 0x0, + 0x0, 0x1f, 0xf3, 0xdf, 0xe0, 0x0, 0x0, 0x0, + 0x6f, 0xf1, 0xdf, 0xf8, 0x0, 0x0, 0x2, 0xef, + 0xa0, 0xdf, 0xff, 0xa3, 0x12, 0x6e, 0xff, 0x20, + 0xdf, 0x8d, 0xff, 0xff, 0xff, 0xe3, 0x0, 0xdf, + 0x60, 0x7d, 0xfe, 0xc7, 0x10, 0x0, + + /* U+0063 "c" */ + 0x0, 0x3, 0xad, 0xfe, 0xc6, 0x0, 0x0, 0x9f, + 0xff, 0xff, 0xff, 0xc1, 0x9, 0xff, 0x93, 0x12, + 0x7f, 0xfa, 0x4f, 0xf6, 0x0, 0x0, 0x3, 0x91, + 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, + 0x0, 0x0, 0x0, 0x0, 0xff, 0x50, 0x0, 0x0, + 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, + 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf6, + 0x0, 0x0, 0x2, 0x91, 0x9, 0xff, 0x93, 0x12, + 0x7f, 0xfa, 0x0, 0x9f, 0xff, 0xff, 0xff, 0xc1, + 0x0, 0x3, 0xad, 0xfe, 0xc6, 0x0, + + /* U+0064 "d" */ + 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x2f, 0xf3, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x2f, 0xf3, 0x0, 0x5, 0xbe, 0xfe, 0x92, + 0x2f, 0xf3, 0x1, 0xbf, 0xff, 0xff, 0xff, 0x7f, + 0xf3, 0xb, 0xff, 0x93, 0x12, 0x7f, 0xff, 0xf3, + 0x5f, 0xf6, 0x0, 0x0, 0x3, 0xff, 0xf3, 0xbf, + 0xc0, 0x0, 0x0, 0x0, 0x8f, 0xf3, 0xdf, 0x70, + 0x0, 0x0, 0x0, 0x3f, 0xf3, 0xff, 0x50, 0x0, + 0x0, 0x0, 0x1f, 0xf3, 0xdf, 0x70, 0x0, 0x0, + 0x0, 0x3f, 0xf3, 0xbf, 0xb0, 0x0, 0x0, 0x0, + 0x7f, 0xf3, 0x5f, 0xf5, 0x0, 0x0, 0x2, 0xef, + 0xf3, 0xb, 0xff, 0x71, 0x0, 0x5e, 0xff, 0xf3, + 0x1, 0xbf, 0xff, 0xef, 0xff, 0x7f, 0xf3, 0x0, + 0x5, 0xbe, 0xfe, 0xa3, 0xf, 0xf3, + + /* U+0065 "e" */ + 0x0, 0x5, 0xbe, 0xfd, 0xa3, 0x0, 0x0, 0xa, + 0xff, 0xff, 0xff, 0xf8, 0x0, 0xa, 0xfe, 0x61, + 0x2, 0x8f, 0xf7, 0x4, 0xff, 0x20, 0x0, 0x0, + 0x5f, 0xf1, 0xaf, 0x90, 0x0, 0x0, 0x0, 0xcf, + 0x6d, 0xfc, 0xbb, 0xbb, 0xbb, 0xbd, 0xf9, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xad, 0xf6, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xaf, 0xc0, 0x0, 0x0, + 0x0, 0x0, 0x4, 0xff, 0x60, 0x0, 0x0, 0x6, + 0x0, 0xa, 0xff, 0xa3, 0x11, 0x4b, 0xf8, 0x0, + 0x9, 0xff, 0xff, 0xff, 0xff, 0x40, 0x0, 0x3, + 0xad, 0xff, 0xd8, 0x10, 0x0, + + /* U+0066 "f" */ + 0x0, 0x0, 0x8d, 0xfe, 0xa1, 0x0, 0xb, 0xff, + 0xff, 0xf0, 0x0, 0x4f, 0xf5, 0x0, 0x30, 0x0, + 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xc0, 0x0, + 0x0, 0xaf, 0xff, 0xff, 0xff, 0x70, 0x9e, 0xff, + 0xfe, 0xee, 0x60, 0x0, 0x7f, 0xd0, 0x0, 0x0, + 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, + 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, + 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, + 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, + 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, + 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, + 0x0, 0x0, + + /* U+0067 "g" */ + 0x0, 0x5, 0xbe, 0xfe, 0xa3, 0xd, 0xf5, 0x0, + 0xbf, 0xff, 0xff, 0xff, 0x8d, 0xf5, 0xb, 0xff, + 0x93, 0x12, 0x6e, 0xff, 0xf5, 0x4f, 0xf6, 0x0, + 0x0, 0x1, 0xef, 0xf5, 0xbf, 0xc0, 0x0, 0x0, + 0x0, 0x5f, 0xf5, 0xdf, 0x70, 0x0, 0x0, 0x0, + 0xf, 0xf5, 0xff, 0x50, 0x0, 0x0, 0x0, 0xe, + 0xf5, 0xdf, 0x70, 0x0, 0x0, 0x0, 0xf, 0xf5, + 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x5f, 0xf5, 0x4f, + 0xf6, 0x0, 0x0, 0x1, 0xef, 0xf5, 0xa, 0xff, + 0xa3, 0x12, 0x6e, 0xff, 0xf5, 0x0, 0xbf, 0xff, + 0xff, 0xff, 0x8f, 0xf5, 0x0, 0x5, 0xbe, 0xfe, + 0xa3, 0xf, 0xf4, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x2f, 0xf1, 0x3, 0x10, 0x0, 0x0, 0x0, 0xaf, + 0xd0, 0xd, 0xf9, 0x52, 0x11, 0x4b, 0xff, 0x50, + 0xa, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x0, 0x0, + 0x28, 0xce, 0xff, 0xd9, 0x30, 0x0, + + /* U+0068 "h" */ + 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, + 0x0, 0x0, 0x0, 0xd, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, + 0xd, 0xf7, 0x18, 0xdf, 0xfc, 0x70, 0x0, 0xdf, + 0xae, 0xff, 0xff, 0xff, 0xc0, 0xd, 0xff, 0xf8, + 0x31, 0x4a, 0xff, 0x90, 0xdf, 0xf5, 0x0, 0x0, + 0xa, 0xff, 0xd, 0xfc, 0x0, 0x0, 0x0, 0x3f, + 0xf2, 0xdf, 0x80, 0x0, 0x0, 0x1, 0xff, 0x3d, + 0xf7, 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, + 0x0, 0x0, 0x0, 0xff, 0x4d, 0xf7, 0x0, 0x0, + 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x0, + 0xff, 0x4d, 0xf7, 0x0, 0x0, 0x0, 0xf, 0xf4, + 0xdf, 0x70, 0x0, 0x0, 0x0, 0xff, 0x4d, 0xf7, + 0x0, 0x0, 0x0, 0xf, 0xf4, + + /* U+0069 "i" */ + 0xb, 0xf6, 0x2f, 0xfd, 0xb, 0xf7, 0x0, 0x0, + 0x0, 0x0, 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, + 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, + 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, 0xd, 0xf7, + 0xd, 0xf7, 0xd, 0xf7, + + /* U+006A "j" */ + 0x0, 0x0, 0x9, 0xf8, 0x0, 0x0, 0x1, 0xff, + 0xf0, 0x0, 0x0, 0xa, 0xf8, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xbf, 0x90, 0x0, 0x0, 0xb, 0xf9, 0x0, + 0x0, 0x0, 0xbf, 0x90, 0x0, 0x0, 0xb, 0xf9, + 0x0, 0x0, 0x0, 0xbf, 0x90, 0x0, 0x0, 0xb, + 0xf9, 0x0, 0x0, 0x0, 0xbf, 0x90, 0x0, 0x0, + 0xb, 0xf9, 0x0, 0x0, 0x0, 0xbf, 0x90, 0x0, + 0x0, 0xb, 0xf9, 0x0, 0x0, 0x0, 0xbf, 0x90, + 0x0, 0x0, 0xb, 0xf9, 0x0, 0x0, 0x0, 0xbf, + 0x90, 0x0, 0x0, 0xb, 0xf9, 0x0, 0x0, 0x0, + 0xdf, 0x80, 0x4, 0x20, 0x5f, 0xf4, 0x0, 0xef, + 0xff, 0xfc, 0x0, 0x9, 0xef, 0xe9, 0x0, 0x0, + + /* U+006B "k" */ + 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, 0x70, 0x0, + 0x0, 0x0, 0x0, 0xd, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, + 0xd, 0xf7, 0x0, 0x0, 0x3, 0xef, 0xa0, 0xdf, + 0x70, 0x0, 0x3, 0xff, 0xb0, 0xd, 0xf7, 0x0, + 0x4, 0xff, 0xb0, 0x0, 0xdf, 0x70, 0x5, 0xff, + 0xb0, 0x0, 0xd, 0xf7, 0x6, 0xff, 0xb0, 0x0, + 0x0, 0xdf, 0x77, 0xff, 0xf1, 0x0, 0x0, 0xd, + 0xfe, 0xff, 0xff, 0xb0, 0x0, 0x0, 0xdf, 0xff, + 0x87, 0xff, 0x70, 0x0, 0xd, 0xff, 0x70, 0xa, + 0xff, 0x40, 0x0, 0xdf, 0x90, 0x0, 0xd, 0xfe, + 0x10, 0xd, 0xf7, 0x0, 0x0, 0x2e, 0xfc, 0x0, + 0xdf, 0x70, 0x0, 0x0, 0x4f, 0xf9, 0xd, 0xf7, + 0x0, 0x0, 0x0, 0x7f, 0xf5, + + /* U+006C "l" */ + 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, + 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, + 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, 0xdf, 0x7d, 0xf7, + 0xdf, 0x7d, 0xf7, + + /* U+006D "m" */ + 0xdf, 0x61, 0x9d, 0xfe, 0xb5, 0x0, 0x7, 0xcf, + 0xfd, 0x80, 0x0, 0xdf, 0xaf, 0xff, 0xff, 0xff, + 0x92, 0xef, 0xff, 0xff, 0xfd, 0x10, 0xdf, 0xfe, + 0x60, 0x3, 0xcf, 0xff, 0xfa, 0x20, 0x17, 0xff, + 0xa0, 0xdf, 0xf3, 0x0, 0x0, 0xe, 0xff, 0xa0, + 0x0, 0x0, 0x8f, 0xf0, 0xdf, 0xc0, 0x0, 0x0, + 0x9, 0xff, 0x20, 0x0, 0x0, 0x2f, 0xf3, 0xdf, + 0x80, 0x0, 0x0, 0x7, 0xff, 0x0, 0x0, 0x0, + 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x6, 0xfe, + 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, + 0x0, 0x6, 0xfe, 0x0, 0x0, 0x0, 0xf, 0xf4, + 0xdf, 0x70, 0x0, 0x0, 0x6, 0xfe, 0x0, 0x0, + 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x6, + 0xfe, 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, + 0x0, 0x0, 0x6, 0xfe, 0x0, 0x0, 0x0, 0xf, + 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x6, 0xfe, 0x0, + 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, + 0x6, 0xfe, 0x0, 0x0, 0x0, 0xf, 0xf4, + + /* U+006E "n" */ + 0xdf, 0x61, 0x8d, 0xff, 0xc7, 0x0, 0xd, 0xf9, + 0xff, 0xff, 0xff, 0xfc, 0x0, 0xdf, 0xff, 0x61, + 0x2, 0x8f, 0xf9, 0xd, 0xff, 0x40, 0x0, 0x0, + 0x9f, 0xf0, 0xdf, 0xc0, 0x0, 0x0, 0x3, 0xff, + 0x2d, 0xf8, 0x0, 0x0, 0x0, 0x1f, 0xf3, 0xdf, + 0x70, 0x0, 0x0, 0x0, 0xff, 0x4d, 0xf7, 0x0, + 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, 0x0, 0x0, + 0x0, 0xff, 0x4d, 0xf7, 0x0, 0x0, 0x0, 0xf, + 0xf4, 0xdf, 0x70, 0x0, 0x0, 0x0, 0xff, 0x4d, + 0xf7, 0x0, 0x0, 0x0, 0xf, 0xf4, 0xdf, 0x70, + 0x0, 0x0, 0x0, 0xff, 0x40, + + /* U+006F "o" */ + 0x0, 0x4, 0xad, 0xfe, 0xb5, 0x0, 0x0, 0x0, + 0x9f, 0xff, 0xff, 0xff, 0xc1, 0x0, 0xa, 0xff, + 0x93, 0x12, 0x7f, 0xfd, 0x0, 0x4f, 0xf6, 0x0, + 0x0, 0x3, 0xff, 0x80, 0xaf, 0xc0, 0x0, 0x0, + 0x0, 0x8f, 0xe0, 0xdf, 0x70, 0x0, 0x0, 0x0, + 0x3f, 0xf1, 0xff, 0x50, 0x0, 0x0, 0x0, 0x1f, + 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x3f, 0xf1, + 0xaf, 0xc0, 0x0, 0x0, 0x0, 0x8f, 0xe0, 0x4f, + 0xf6, 0x0, 0x0, 0x3, 0xff, 0x80, 0xa, 0xff, + 0x93, 0x12, 0x7f, 0xfd, 0x0, 0x0, 0x9f, 0xff, + 0xff, 0xff, 0xc1, 0x0, 0x0, 0x4, 0xad, 0xfe, + 0xb5, 0x0, 0x0, + + /* U+0070 "p" */ + 0xdf, 0x61, 0x8d, 0xfe, 0xc7, 0x10, 0x0, 0xdf, + 0x8e, 0xff, 0xff, 0xff, 0xe3, 0x0, 0xdf, 0xff, + 0x92, 0x0, 0x5d, 0xfe, 0x20, 0xdf, 0xf7, 0x0, + 0x0, 0x1, 0xef, 0xa0, 0xdf, 0xd0, 0x0, 0x0, + 0x0, 0x5f, 0xf1, 0xdf, 0x90, 0x0, 0x0, 0x0, + 0x1f, 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, 0xf, + 0xf5, 0xdf, 0x90, 0x0, 0x0, 0x0, 0x1f, 0xf3, + 0xdf, 0xe0, 0x0, 0x0, 0x0, 0x6f, 0xf1, 0xdf, + 0xf8, 0x0, 0x0, 0x2, 0xef, 0xa0, 0xdf, 0xff, + 0xa3, 0x12, 0x6e, 0xff, 0x20, 0xdf, 0x9d, 0xff, + 0xff, 0xff, 0xe3, 0x0, 0xdf, 0x70, 0x7c, 0xfe, + 0xc7, 0x10, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xdf, 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, 0xdf, + 0x70, 0x0, 0x0, 0x0, 0x0, 0x0, + + /* U+0071 "q" */ + 0x0, 0x5, 0xbe, 0xfe, 0xa2, 0xf, 0xf3, 0x1, + 0xbf, 0xff, 0xff, 0xff, 0x6f, 0xf3, 0xb, 0xff, + 0x93, 0x12, 0x7f, 0xff, 0xf3, 0x5f, 0xf6, 0x0, + 0x0, 0x3, 0xff, 0xf3, 0xbf, 0xc0, 0x0, 0x0, + 0x0, 0x8f, 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, + 0x3f, 0xf3, 0xff, 0x50, 0x0, 0x0, 0x0, 0x1f, + 0xf3, 0xdf, 0x70, 0x0, 0x0, 0x0, 0x3f, 0xf3, + 0xbf, 0xc0, 0x0, 0x0, 0x0, 0x8f, 0xf3, 0x5f, + 0xf6, 0x0, 0x0, 0x3, 0xff, 0xf3, 0xb, 0xff, + 0x93, 0x12, 0x7f, 0xff, 0xf3, 0x1, 0xbf, 0xff, + 0xff, 0xff, 0x7f, 0xf3, 0x0, 0x5, 0xbe, 0xfe, + 0x92, 0x2f, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x2f, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, + 0xf3, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x2f, 0xf3, + + /* U+0072 "r" */ + 0xdf, 0x61, 0x8d, 0xf0, 0xdf, 0x7e, 0xff, 0xf0, + 0xdf, 0xff, 0xb5, 0x40, 0xdf, 0xf7, 0x0, 0x0, + 0xdf, 0xd0, 0x0, 0x0, 0xdf, 0x90, 0x0, 0x0, + 0xdf, 0x70, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, + 0xdf, 0x70, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, + 0xdf, 0x70, 0x0, 0x0, 0xdf, 0x70, 0x0, 0x0, + 0xdf, 0x70, 0x0, 0x0, + + /* U+0073 "s" */ + 0x0, 0x18, 0xcf, 0xfe, 0xb7, 0x10, 0x2, 0xef, + 0xff, 0xff, 0xff, 0xb0, 0xb, 0xfe, 0x41, 0x2, + 0x6c, 0x30, 0xf, 0xf5, 0x0, 0x0, 0x0, 0x0, + 0xe, 0xf9, 0x0, 0x0, 0x0, 0x0, 0x8, 0xff, + 0xd9, 0x52, 0x0, 0x0, 0x0, 0x8f, 0xff, 0xff, + 0xe9, 0x10, 0x0, 0x0, 0x47, 0xad, 0xff, 0xc0, + 0x0, 0x0, 0x0, 0x0, 0x5f, 0xf3, 0x1, 0x0, + 0x0, 0x0, 0xf, 0xf4, 0xe, 0xc6, 0x20, 0x3, + 0xaf, 0xf1, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x60, + 0x1, 0x7b, 0xef, 0xfd, 0x92, 0x0, + + /* U+0074 "t" */ + 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, + 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0xaf, + 0xff, 0xff, 0xff, 0x70, 0x9e, 0xff, 0xfe, 0xee, + 0x60, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, + 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, + 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xd0, + 0x0, 0x0, 0x0, 0x7f, 0xd0, 0x0, 0x0, 0x0, + 0x7f, 0xd0, 0x0, 0x0, 0x0, 0x7f, 0xe0, 0x0, + 0x0, 0x0, 0x4f, 0xf7, 0x1, 0x50, 0x0, 0xc, + 0xff, 0xff, 0xf1, 0x0, 0x0, 0x9e, 0xfd, 0x81, + + /* U+0075 "u" */ + 0xff, 0x60, 0x0, 0x0, 0x4, 0xff, 0xf, 0xf6, + 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xff, 0x60, 0x0, + 0x0, 0x4, 0xff, 0xf, 0xf6, 0x0, 0x0, 0x0, + 0x4f, 0xf0, 0xff, 0x60, 0x0, 0x0, 0x4, 0xff, + 0xf, 0xf6, 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xff, + 0x60, 0x0, 0x0, 0x4, 0xff, 0xe, 0xf6, 0x0, + 0x0, 0x0, 0x5f, 0xf0, 0xdf, 0x80, 0x0, 0x0, + 0x8, 0xff, 0xa, 0xfe, 0x0, 0x0, 0x1, 0xef, + 0xf0, 0x3f, 0xfb, 0x20, 0x4, 0xdf, 0xff, 0x0, + 0x8f, 0xff, 0xff, 0xff, 0x9f, 0xf0, 0x0, 0x4b, + 0xef, 0xea, 0x32, 0xff, 0x0, + + /* U+0076 "v" */ + 0xd, 0xf9, 0x0, 0x0, 0x0, 0x1, 0xff, 0x30, + 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x7f, 0xc0, 0x0, + 0xef, 0x60, 0x0, 0x0, 0xd, 0xf5, 0x0, 0x8, + 0xfd, 0x0, 0x0, 0x5, 0xfe, 0x0, 0x0, 0x2f, + 0xf3, 0x0, 0x0, 0xbf, 0x80, 0x0, 0x0, 0xbf, + 0xa0, 0x0, 0x2f, 0xf1, 0x0, 0x0, 0x4, 0xff, + 0x10, 0x9, 0xfa, 0x0, 0x0, 0x0, 0xd, 0xf7, + 0x1, 0xff, 0x30, 0x0, 0x0, 0x0, 0x6f, 0xe0, + 0x7f, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xff, 0x5d, + 0xf5, 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, 0xfe, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x2f, 0xff, 0x80, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xbf, 0xf1, 0x0, + 0x0, 0x0, + + /* U+0077 "w" */ + 0xaf, 0x80, 0x0, 0x0, 0x5, 0xff, 0x0, 0x0, + 0x0, 0xc, 0xf4, 0x5f, 0xd0, 0x0, 0x0, 0xb, + 0xff, 0x50, 0x0, 0x0, 0x2f, 0xe0, 0xe, 0xf3, + 0x0, 0x0, 0x1f, 0xff, 0xb0, 0x0, 0x0, 0x8f, + 0x80, 0x9, 0xf9, 0x0, 0x0, 0x7f, 0xbf, 0xf1, + 0x0, 0x0, 0xef, 0x20, 0x3, 0xfe, 0x0, 0x0, + 0xcf, 0x4b, 0xf7, 0x0, 0x4, 0xfc, 0x0, 0x0, + 0xdf, 0x40, 0x2, 0xfe, 0x5, 0xfc, 0x0, 0xa, + 0xf6, 0x0, 0x0, 0x7f, 0xa0, 0x8, 0xf8, 0x0, + 0xef, 0x20, 0xf, 0xf1, 0x0, 0x0, 0x2f, 0xf0, + 0xe, 0xf2, 0x0, 0x9f, 0x80, 0x5f, 0xb0, 0x0, + 0x0, 0xc, 0xf5, 0x4f, 0xc0, 0x0, 0x3f, 0xe0, + 0xbf, 0x50, 0x0, 0x0, 0x6, 0xfb, 0xaf, 0x60, + 0x0, 0xd, 0xf5, 0xfe, 0x0, 0x0, 0x0, 0x1, + 0xff, 0xff, 0x0, 0x0, 0x7, 0xff, 0xf9, 0x0, + 0x0, 0x0, 0x0, 0xaf, 0xfa, 0x0, 0x0, 0x1, + 0xff, 0xf3, 0x0, 0x0, 0x0, 0x0, 0x4f, 0xf4, + 0x0, 0x0, 0x0, 0xbf, 0xd0, 0x0, 0x0, + + /* U+0078 "x" */ + 0x1e, 0xf8, 0x0, 0x0, 0x4, 0xff, 0x40, 0x4f, + 0xf4, 0x0, 0x1, 0xef, 0x80, 0x0, 0x8f, 0xe1, + 0x0, 0xbf, 0xb0, 0x0, 0x0, 0xcf, 0xb0, 0x7f, + 0xe1, 0x0, 0x0, 0x1, 0xef, 0xaf, 0xf4, 0x0, + 0x0, 0x0, 0x4, 0xff, 0xf7, 0x0, 0x0, 0x0, + 0x0, 0xd, 0xff, 0x10, 0x0, 0x0, 0x0, 0x8, + 0xff, 0xfb, 0x0, 0x0, 0x0, 0x4, 0xff, 0x5e, + 0xf7, 0x0, 0x0, 0x1, 0xef, 0x80, 0x4f, 0xf3, + 0x0, 0x0, 0xcf, 0xc0, 0x0, 0x8f, 0xe1, 0x0, + 0x8f, 0xe1, 0x0, 0x0, 0xcf, 0xb0, 0x4f, 0xf4, + 0x0, 0x0, 0x2, 0xff, 0x80, + + /* U+0079 "y" */ + 0xd, 0xf9, 0x0, 0x0, 0x0, 0x1, 0xff, 0x30, + 0x6f, 0xf0, 0x0, 0x0, 0x0, 0x7f, 0xc0, 0x0, + 0xef, 0x60, 0x0, 0x0, 0xd, 0xf5, 0x0, 0x8, + 0xfd, 0x0, 0x0, 0x4, 0xfe, 0x0, 0x0, 0x2f, + 0xf4, 0x0, 0x0, 0xbf, 0x80, 0x0, 0x0, 0xbf, + 0xb0, 0x0, 0x2f, 0xf1, 0x0, 0x0, 0x4, 0xff, + 0x10, 0x8, 0xfa, 0x0, 0x0, 0x0, 0xd, 0xf8, + 0x0, 0xef, 0x30, 0x0, 0x0, 0x0, 0x6f, 0xe0, + 0x6f, 0xc0, 0x0, 0x0, 0x0, 0x0, 0xef, 0x6c, + 0xf5, 0x0, 0x0, 0x0, 0x0, 0x8, 0xfe, 0xfe, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0x70, + 0x0, 0x0, 0x0, 0x0, 0x0, 0xaf, 0xf1, 0x0, + 0x0, 0x0, 0x0, 0x0, 0xa, 0xfa, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x2, 0xff, 0x30, 0x0, 0x0, + 0x0, 0xa4, 0x2, 0xcf, 0xb0, 0x0, 0x0, 0x0, + 0x5f, 0xff, 0xff, 0xe1, 0x0, 0x0, 0x0, 0x0, + 0x8d, 0xfe, 0x91, 0x0, 0x0, 0x0, 0x0, + + /* U+007A "z" */ + 0xe, 0xff, 0xff, 0xff, 0xff, 0xf6, 0xd, 0xee, + 0xee, 0xee, 0xff, 0xf5, 0x0, 0x0, 0x0, 0x1, + 0xef, 0xa0, 0x0, 0x0, 0x0, 0xc, 0xfd, 0x0, + 0x0, 0x0, 0x0, 0x8f, 0xf2, 0x0, 0x0, 0x0, + 0x5, 0xff, 0x40, 0x0, 0x0, 0x0, 0x2f, 0xf8, + 0x0, 0x0, 0x0, 0x0, 0xdf, 0xb0, 0x0, 0x0, + 0x0, 0xb, 0xfd, 0x10, 0x0, 0x0, 0x0, 0x7f, + 0xf2, 0x0, 0x0, 0x0, 0x4, 0xff, 0x50, 0x0, + 0x0, 0x0, 0xe, 0xff, 0xee, 0xee, 0xee, 0xe8, + 0xf, 0xff, 0xff, 0xff, 0xff, 0xf9, + + /* U+00B0 "°" */ + 0x0, 0x0, 0x0, 0x0, 0x2, 0xbf, 0xfb, 0x20, + 0x1e, 0xc5, 0x5c, 0xe2, 0x9d, 0x0, 0x0, 0xda, + 0xd8, 0x0, 0x0, 0x7e, 0xd7, 0x0, 0x0, 0x7e, + 0xac, 0x0, 0x0, 0xcb, 0x3f, 0xa2, 0x2a, 0xf3, + 0x4, 0xef, 0xfe, 0x40, 0x0, 0x2, 0x20, 0x0, + + /* U+00E9 "é" */ + 0x0, 0x0, 0x0, 0xa, 0xfe, 0x30, 0x0, 0x0, + 0x0, 0xa, 0xfc, 0x10, 0x0, 0x0, 0x0, 0xa, + 0xf9, 0x0, 0x0, 0x0, 0x0, 0x1, 0x33, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x5b, 0xef, 0xda, 0x30, 0x0, 0x0, + 0xaf, 0xff, 0xff, 0xff, 0x80, 0x0, 0xaf, 0xe6, + 0x10, 0x28, 0xff, 0x70, 0x4f, 0xf2, 0x0, 0x0, + 0x5, 0xff, 0x1a, 0xf9, 0x0, 0x0, 0x0, 0xc, + 0xf6, 0xdf, 0xcb, 0xbb, 0xbb, 0xbb, 0xdf, 0x9f, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, 0xdf, 0x60, + 0x0, 0x0, 0x0, 0x0, 0xa, 0xfc, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x4f, 0xf6, 0x0, 0x0, 0x0, + 0x60, 0x0, 0xaf, 0xfa, 0x31, 0x14, 0xbf, 0x80, + 0x0, 0x9f, 0xff, 0xff, 0xff, 0xf4, 0x0, 0x0, + 0x3a, 0xdf, 0xfd, 0x81, 0x0, + + /* U+00FB "û" */ + 0x0, 0x0, 0x8f, 0xfa, 0x0, 0x0, 0x0, 0x0, + 0x9f, 0xba, 0xfa, 0x0, 0x0, 0x0, 0x9f, 0x90, + 0x7, 0xfa, 0x0, 0x0, 0x2, 0x20, 0x0, 0x1, + 0x20, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0xf, 0xf6, 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xff, + 0x60, 0x0, 0x0, 0x4, 0xff, 0xf, 0xf6, 0x0, + 0x0, 0x0, 0x4f, 0xf0, 0xff, 0x60, 0x0, 0x0, + 0x4, 0xff, 0xf, 0xf6, 0x0, 0x0, 0x0, 0x4f, + 0xf0, 0xff, 0x60, 0x0, 0x0, 0x4, 0xff, 0xf, + 0xf6, 0x0, 0x0, 0x0, 0x4f, 0xf0, 0xef, 0x60, + 0x0, 0x0, 0x5, 0xff, 0xd, 0xf8, 0x0, 0x0, + 0x0, 0x8f, 0xf0, 0xaf, 0xe0, 0x0, 0x0, 0x1e, + 0xff, 0x3, 0xff, 0xb2, 0x0, 0x4d, 0xff, 0xf0, + 0x8, 0xff, 0xff, 0xff, 0xf9, 0xff, 0x0, 0x4, + 0xbe, 0xfe, 0xa3, 0x2f, 0xf0, + + /* U+F015 "" */ + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x9f, 0x90, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x1c, 0xff, 0xfb, 0x10, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, 0xdf, + 0xff, 0xff, 0xd1, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x3e, 0xff, 0xff, 0xff, + 0xfe, 0x30, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x4, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf4, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x6f, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x60, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x8, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf8, 0x0, 0x0, 0x0, + 0x0, 0x0, 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0x90, 0x0, 0x0, 0x0, 0x1c, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xfb, 0x0, 0x0, 0x2, 0xdf, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xd1, 0x0, 0x3e, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x20, + 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xd0, 0xdf, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xd0, 0x27, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x87, 0x10, 0x0, 0xf, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0, 0x0, + 0x0, 0xf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, + 0xff, 0xff, 0xff, 0xfa, 0x88, 0x8a, 0xff, 0xff, + 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, 0xff, 0xff, + 0xff, 0xa0, 0x0, 0x0, 0xaf, 0xff, 0xff, 0xff, + 0x0, 0x0, 0x0, 0xf, 0xff, 0xff, 0xff, 0x80, + 0x0, 0x0, 0x8f, 0xff, 0xff, 0xff, 0x0, 0x0, + 0x0, 0xf, 0xff, 0xff, 0xff, 0x80, 0x0, 0x0, + 0x8f, 0xff, 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, + 0xff, 0xff, 0xff, 0x80, 0x0, 0x0, 0x8f, 0xff, + 0xff, 0xff, 0x0, 0x0, 0x0, 0xf, 0xff, 0xff, + 0xff, 0x80, 0x0, 0x0, 0x8f, 0xff, 0xff, 0xff, + 0x0, 0x0, 0x0, 0xe, 0xff, 0xff, 0xff, 0x60, + 0x0, 0x0, 0x6f, 0xff, 0xff, 0xfe, 0x0, 0x0, + 0x0, 0x5, 0xef, 0xff, 0xfb, 0x0, 0x0, 0x0, + 0xb, 0xff, 0xff, 0xe5, 0x0, 0x0, + + /* U+F0C2 "" */ + 0x0, 0x0, 0x0, 0x0, 0x3, 0x8a, 0xa8, 0x30, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x3, 0xcf, 0xff, 0xff, 0xfc, 0x20, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x4f, 0xff, 0xff, 0xff, 0xff, 0xf4, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x2, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x36, 0xaa, + 0x60, 0x0, 0x0, 0x0, 0x0, 0x0, 0xb, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, + 0x20, 0x0, 0x0, 0x0, 0x0, 0x1f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xd0, + 0x0, 0x0, 0x0, 0x0, 0x5f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf4, 0x0, + 0x0, 0x0, 0x0, 0x7f, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xf7, 0x0, 0x0, + 0x0, 0x4, 0xdf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf6, 0x0, 0x0, 0x0, + 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf9, 0x20, 0x0, 0x9, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf8, 0x0, 0x4f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0x90, 0xaf, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf4, 0xef, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xfb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xfe, 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfd, 0x4f, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0xa, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf1, 0x0, 0xbf, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0x40, 0x0, 0x6, 0xdf, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xb2, 0x0, 0x0, 0x0, 0x2, 0x44, 0x44, + 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x31, + 0x0, 0x0, + + /* U+F575 "" */ + 0x2, 0xdd, 0x30, 0x0, 0x0, 0x0, 0x20, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x7, 0xff, 0xf3, 0x0, + 0x0, 0x4e, 0xff, 0xa0, 0x0, 0x0, 0x0, 0x0, + 0x2, 0xff, 0xfe, 0x30, 0x5, 0xff, 0xff, 0xfc, + 0x10, 0x0, 0x0, 0x0, 0x0, 0x3e, 0xff, 0xe3, + 0x5f, 0xff, 0xef, 0xff, 0xc0, 0x0, 0x0, 0x0, + 0x0, 0x3, 0xef, 0xff, 0xff, 0xfc, 0x15, 0xff, + 0xfc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x3e, 0xff, + 0xff, 0xc1, 0x0, 0x6f, 0xff, 0xc0, 0x0, 0x0, + 0x0, 0x0, 0x8, 0xff, 0xff, 0x40, 0x0, 0x6, + 0xff, 0xfc, 0x0, 0x0, 0x0, 0x0, 0x5f, 0xff, + 0xff, 0xe3, 0x0, 0x0, 0x6f, 0xff, 0xc0, 0x0, + 0x0, 0x5, 0xff, 0xfc, 0xef, 0xfe, 0x30, 0x0, + 0x6, 0xff, 0xfc, 0x0, 0x0, 0x5f, 0xff, 0xc1, + 0x3e, 0xff, 0xa0, 0x0, 0x0, 0x6f, 0xff, 0xa0, + 0x5, 0xff, 0xfc, 0x10, 0x3, 0xef, 0x70, 0x0, + 0x0, 0x6, 0xff, 0xf0, 0x2f, 0xff, 0xc1, 0x0, + 0x0, 0x12, 0x0, 0x0, 0x0, 0x0, 0xef, 0xf2, + 0xaf, 0xfd, 0x10, 0x0, 0x0, 0x0, 0x0, 0x0, + 0x0, 0xc, 0xff, 0xe0, 0xdf, 0xfa, 0x77, 0x77, + 0x77, 0x77, 0x77, 0x77, 0x77, 0xcf, 0xff, 0x50, + 0xdf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf6, 0x0, 0x9f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x60, 0x0, + 0x1e, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xf6, 0x0, 0x0, 0x3, 0xef, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x60, 0x0, 0x0, + 0x0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf6, 0x0, 0x0, 0x0, 0x0, 0x3, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x60, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xf6, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x3, 0xff, + 0xff, 0xff, 0xff, 0x60, 0x0, 0x0, 0x0, 0x0, + 0x0, 0x0, 0x0, 0x3e, 0xff, 0xff, 0xf6, 0x0, + 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1, + 0x9e, 0xeb, 0x30, 0x0, 0x0, 0x0, 0x0, 0x0 +}; + + +/*--------------------- + * GLYPH DESCRIPTION + *--------------------*/ + +static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { + {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, + {.bitmap_index = 0, .adv_w = 103, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 0, .adv_w = 324, .box_w = 20, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 170, .adv_w = 81, .box_w = 3, .box_h = 7, .ofs_x = 1, .ofs_y = 10}, + {.bitmap_index = 181, .adv_w = 87, .box_w = 4, .box_h = 7, .ofs_x = 1, .ofs_y = -4}, + {.bitmap_index = 195, .adv_w = 87, .box_w = 4, .box_h = 4, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 203, .adv_w = 256, .box_w = 14, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 322, .adv_w = 142, .box_w = 7, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 382, .adv_w = 220, .box_w = 13, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 493, .adv_w = 220, .box_w = 13, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 604, .adv_w = 257, .box_w = 16, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 740, .adv_w = 220, .box_w = 13, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 851, .adv_w = 237, .box_w = 14, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 970, .adv_w = 230, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1089, .adv_w = 247, .box_w = 14, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1208, .adv_w = 237, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 1327, .adv_w = 281, .box_w = 19, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 1489, .adv_w = 291, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 1617, .adv_w = 278, .box_w = 16, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1753, .adv_w = 317, .box_w = 17, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 1898, .adv_w = 257, .box_w = 13, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2009, .adv_w = 244, .box_w = 13, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2120, .adv_w = 296, .box_w = 16, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 2256, .adv_w = 312, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2384, .adv_w = 119, .box_w = 3, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2410, .adv_w = 197, .box_w = 11, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 2504, .adv_w = 276, .box_w = 16, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2640, .adv_w = 228, .box_w = 13, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2751, .adv_w = 367, .box_w = 19, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 2913, .adv_w = 312, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 3041, .adv_w = 323, .box_w = 19, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 3203, .adv_w = 277, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 3331, .adv_w = 323, .box_w = 19, .box_h = 20, .ofs_x = 1, .ofs_y = -3}, + {.bitmap_index = 3521, .adv_w = 279, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 3649, .adv_w = 238, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3768, .adv_w = 225, .box_w = 14, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 3887, .adv_w = 304, .box_w = 15, .box_h = 17, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 4015, .adv_w = 273, .box_w = 19, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 4177, .adv_w = 432, .box_w = 27, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 4407, .adv_w = 258, .box_w = 16, .box_h = 17, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 4543, .adv_w = 248, .box_w = 17, .box_h = 17, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 4688, .adv_w = 252, .box_w = 15, .box_h = 17, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 4816, .adv_w = 230, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 4894, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 5020, .adv_w = 219, .box_w = 12, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 5098, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 5224, .adv_w = 235, .box_w = 13, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 5309, .adv_w = 136, .box_w = 10, .box_h = 18, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 5399, .adv_w = 265, .box_w = 14, .box_h = 18, .ofs_x = 1, .ofs_y = -5}, + {.bitmap_index = 5525, .adv_w = 262, .box_w = 13, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 5642, .adv_w = 107, .box_w = 4, .box_h = 18, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 5678, .adv_w = 109, .box_w = 9, .box_h = 23, .ofs_x = -3, .ofs_y = -5}, + {.bitmap_index = 5782, .adv_w = 237, .box_w = 13, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 5899, .adv_w = 107, .box_w = 3, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 5926, .adv_w = 406, .box_w = 22, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 6069, .adv_w = 262, .box_w = 13, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 6154, .adv_w = 244, .box_w = 14, .box_h = 13, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 6245, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 2, .ofs_y = -5}, + {.bitmap_index = 6371, .adv_w = 262, .box_w = 14, .box_h = 18, .ofs_x = 1, .ofs_y = -5}, + {.bitmap_index = 6497, .adv_w = 157, .box_w = 8, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 6549, .adv_w = 192, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 6627, .adv_w = 159, .box_w = 10, .box_h = 16, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 6707, .adv_w = 260, .box_w = 13, .box_h = 13, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 6792, .adv_w = 215, .box_w = 15, .box_h = 13, .ofs_x = -1, .ofs_y = 0}, + {.bitmap_index = 6890, .adv_w = 345, .box_w = 22, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 7033, .adv_w = 212, .box_w = 13, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 7118, .adv_w = 215, .box_w = 15, .box_h = 18, .ofs_x = -1, .ofs_y = -5}, + {.bitmap_index = 7253, .adv_w = 200, .box_w = 12, .box_h = 13, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 7331, .adv_w = 161, .box_w = 8, .box_h = 10, .ofs_x = 1, .ofs_y = 9}, + {.bitmap_index = 7371, .adv_w = 235, .box_w = 13, .box_h = 18, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 7488, .adv_w = 260, .box_w = 13, .box_h = 18, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 7605, .adv_w = 432, .box_w = 28, .box_h = 25, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 7955, .adv_w = 480, .box_w = 30, .box_h = 22, .ofs_x = 0, .ofs_y = -2}, + {.bitmap_index = 8285, .adv_w = 384, .box_w = 24, .box_h = 24, .ofs_x = 0, .ofs_y = -3} +}; + +/*--------------------- + * CHARACTER MAPPING + *--------------------*/ + +static const uint8_t glyph_id_ofs_list_0[] = { + 0, 0, 0, 0, 0, 1, 0, 2, + 0, 0, 0, 0, 3, 0, 4, 0, + 5, 6, 7, 8, 9, 10, 11, 12, + 13, 14 +}; + +static const uint16_t unicode_list_3[] = { + 0x0, 0x39, 0x4b, 0xef65, 0xf012, 0xf4c5 +}; + +/*Collect the unicode lists and glyph_id offsets*/ +static const lv_font_fmt_txt_cmap_t cmaps[] = +{ + { + .range_start = 32, .range_length = 26, .glyph_id_start = 1, + .unicode_list = NULL, .glyph_id_ofs_list = glyph_id_ofs_list_0, .list_length = 26, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_FULL + }, + { + .range_start = 65, .range_length = 26, .glyph_id_start = 16, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 97, .range_length = 26, .glyph_id_start = 42, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 176, .range_length = 62662, .glyph_id_start = 68, + .unicode_list = unicode_list_3, .glyph_id_ofs_list = NULL, .list_length = 6, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY + } +}; + +/*----------------- + * KERNING + *----------------*/ + + +/*Map glyph_ids to kern left classes*/ +static const uint8_t kern_left_class_mapping[] = +{ + 0, 0, 1, 2, 3, 3, 4, 0, + 5, 6, 7, 8, 9, 10, 11, 4, + 12, 13, 14, 15, 16, 17, 18, 19, + 19, 20, 21, 22, 19, 19, 15, 23, + 15, 24, 25, 26, 20, 27, 27, 28, + 29, 30, 31, 32, 33, 34, 35, 36, + 37, 31, 37, 37, 38, 34, 31, 31, + 32, 32, 39, 40, 41, 42, 37, 43, + 43, 44, 43, 45, 46, 35, 37, 0, + 0, 0 +}; + +/*Map glyph_ids to kern right classes*/ +static const uint8_t kern_right_class_mapping[] = +{ + 0, 0, 1, 2, 3, 3, 4, 5, + 6, 7, 8, 9, 4, 10, 11, 12, + 13, 14, 15, 14, 14, 14, 15, 14, + 14, 16, 14, 14, 14, 14, 15, 14, + 15, 14, 17, 18, 19, 20, 20, 21, + 22, 23, 24, 25, 26, 26, 26, 0, + 26, 25, 27, 28, 25, 25, 29, 29, + 26, 29, 26, 29, 30, 31, 32, 33, + 33, 34, 33, 35, 36, 26, 32, 0, + 0, 0 +}; + +/*Kern values between classes*/ +static const int8_t kern_class_values[] = +{ + -46, -10, 12, 0, -8, 4, 4, 13, + 8, -7, 8, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -10, 10, 17, -21, 3, + 18, 8, 7, -15, 3, 19, 1, 16, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 8, + -24, -21, 0, -5, -5, 4, 4, -3, + 0, -5, 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -24, 0, 3, -5, 0, + -1, -1, -4, 0, 0, -3, 0, 0, + -3, 0, 0, -9, 0, -8, 0, -10, + -13, -13, -7, 0, 0, 0, 0, -3, + 0, 0, 4, 0, 3, -4, 0, 1, + 4, 0, 4, -1, 0, 0, 0, -7, + 0, -1, 0, 0, 1, 0, 0, 5, + 0, -3, 0, -5, 0, -7, 0, 0, + 0, -4, 0, 0, 0, 0, 0, -1, + 1, -3, -3, 0, -4, -4, 0, 0, + 0, -2, -2, 0, -4, -5, 0, 0, + 1, 0, 0, 0, 0, -3, 0, -4, + -4, -4, 0, 0, 0, 0, 0, -2, + 0, 0, 0, 0, -3, -5, 0, -6, + -12, -12, 8, 0, -10, -1, -5, 0, + -1, -18, 4, -3, 0, 0, 4, 1, + -3, -20, 0, -20, -3, -33, -3, 11, + 0, 5, 0, 0, 0, 0, 1, 0, + -7, -5, 0, -12, -4, 0, 0, 0, + 0, -2, -2, 0, -2, -5, 0, 0, + 0, 0, 0, -4, 0, -4, 0, -3, + -5, -3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -3, -3, 0, -5, + -8, -3, 4, 0, 0, 0, 0, 0, + 0, -3, 0, 0, 3, 0, 0, 0, + 0, -4, 0, -4, -3, -5, 0, 0, + 0, 3, 0, -3, 0, 0, 0, 0, + -4, -6, 0, -7, 1, 12, -20, -8, + 4, 0, -3, -25, -7, 0, -7, 0, + -25, 0, -7, -10, -3, 0, 0, 2, + -1, 3, -3, -15, 0, -19, -9, -8, + -9, -12, -5, -10, -1, -7, -10, 2, + -4, 1, 4, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -2, 0, 0, -1, + 0, -4, 0, -7, -8, -8, -1, 0, + 0, 0, 0, -3, 0, 0, 0, 0, + 2, -2, 0, 0, 0, -17, 13, -3, + -16, 0, 4, -6, 0, -19, -2, -5, + 5, 0, -4, 6, 0, -13, -6, -14, + -13, -16, 0, 0, 0, -2, 0, 0, + 0, -2, -2, -4, -10, -13, -1, -36, + 0, 0, 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -4, 0, -2, -4, -6, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 5, -8, + 4, -3, -1, -10, -4, 0, -5, -4, + -7, 0, -6, 0, -1, -3, -1, -3, + -7, -5, 0, -3, 0, -8, 0, 0, + 0, -8, 0, -7, 0, -7, -7, 4, + 0, -7, -8, 0, -4, -4, -5, 0, + 0, 0, 0, 0, -4, 0, 0, -6, + 0, -4, 0, -8, -10, -12, -3, 0, + 0, 0, 0, 31, 0, 0, 2, 0, + 0, -5, 0, 4, 0, 0, 4, -5, + 0, -3, -5, -12, -3, -3, -3, -1, + 0, 0, -1, 0, 0, 0, 0, -4, + -3, -3, 0, -3, 0, -3, 0, 0, + 0, -3, -5, -3, -3, -5, -3, 0, + 0, 15, -4, -5, 6, 0, 0, -18, + -7, 4, -7, 3, -12, 0, -3, -6, + -1, 2, 0, 0, -7, 0, 0, -7, + 0, -7, -4, -6, -4, -4, 0, -7, + 2, -7, -7, 12, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -3, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -3, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -6, 0, 0, 0, 0, -5, 0, 0, + -4, -4, 0, 0, 0, 0, 0, -2, + 0, 0, 0, 0, 0, -3, 0, 0, + 0, 0, 0, -8, 8, 1, -3, -18, + 0, 0, -8, -4, -11, 0, -10, 0, + -6, -17, -4, -15, -15, -18, 0, -5, + 0, -9, -4, -1, -4, -7, -10, -7, + -14, -16, -9, -4, 0, 0, 12, -8, + -14, 0, 1, -12, 0, -19, -3, -4, + 1, 0, -5, 0, -3, -25, -5, -20, + -4, -28, 0, 1, 0, -3, 0, 0, + 0, 0, -2, -3, -15, -3, 0, -25, + 0, 0, -11, 0, 0, -2, -6, -12, + -4, 0, -3, 0, -17, -4, 0, -13, + 0, -12, -3, -7, -10, -4, -7, -6, + 0, -5, -7, -4, -7, 0, 2, 0, + -3, -13, 0, 8, 0, 0, 0, 0, + 0, 0, -3, -8, 0, 0, 0, 0, + 0, 0, 0, -4, 0, -4, 0, 0, + -8, -4, 0, -2, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, 0, 6, + 0, -12, 8, 0, -4, 0, -3, 4, + 0, -4, 0, -4, 0, 0, 0, 0, + 0, -4, 0, 0, -5, -6, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -4, -4, 0, -6, 0, 3, -12, -8, + 15, 7, 4, -33, -3, 8, -4, 0, + -13, 0, -4, -4, -3, 4, -5, -3, + -12, -3, 0, -11, 0, -21, -5, 11, + -5, -15, 1, -5, -13, -13, -4, 15, + 0, 0, -14, -10, 12, 0, 1, -28, + -3, 4, -7, -3, -14, -6, -8, -6, + -6, -3, 0, 0, -9, -8, -4, -21, + 0, -21, -5, 0, -13, -22, -1, -12, + -7, -13, -11, 10, 0, 0, 0, -13, + 4, 0, 0, -20, 0, -4, -8, -7, + -13, -9, -10, 0, -5, -12, -4, -9, + -7, -12, -4, -7, 0, -12, -4, 0, + -4, -8, -9, -10, -11, -15, -5, -8, + 0, 0, -14, -13, 13, -4, 2, -36, + -7, 8, -8, -7, -16, -5, -12, -4, + -6, -3, -4, -8, -12, -1, 0, -25, + 0, -23, -9, 9, -15, -26, -8, -13, + -16, -19, -13, 8, 0, 0, 8, -7, + 8, 0, 0, -12, -1, 0, -1, 0, + 0, 0, -3, 0, 0, 0, 0, 0, + -4, 0, 0, 1, 0, -5, 0, 0, + 0, 0, -3, -3, -5, 0, 0, 0, + -11, 0, 0, 0, -8, -2, 0, 0, + 0, -8, 0, -5, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 1, 0, 0, 0, 0, 0, 0, + -4, 0, 0, -7, -10, -6, -5, 0, + -10, -4, -9, 0, 0, -10, 0, -4, + -4, 0, 0, 0, 0, -31, -7, -15, + -4, -14, 0, -2, 0, 0, 0, 0, + 0, 0, 0, 0, -6, -7, -3, -7, + 0, 0, 8, -3, -9, -3, -7, -7, + 0, -5, -2, -3, 0, 0, -1, 0, + 0, -34, -3, -5, 0, -8, 0, 0, + -3, -3, 0, 0, 0, 0, 3, 0, + -3, -7, -3, 7, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 5, 0, 0, 0, 0, 0, + -3, -8, 0, 0, -10, -4, -8, 0, + 0, -11, 0, -4, 0, 0, 0, 0, + 0, -37, 0, -8, -14, -19, 0, -6, + 0, 0, 0, 0, 0, 0, 0, 0, + -4, -6, -2, -6, 7, 0, -4, 5, + 19, 7, 8, -10, 5, 16, 5, 11, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -4, 0, -3, 31, 17, + 31, 0, 0, 0, 4, 0, 0, 14, + 0, 0, 0, 0, -3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -6, -32, -5, -3, -16, -19, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 4, -4, + 3, 7, 4, -12, 0, -1, -3, 4, + 0, 0, 0, 0, 0, -10, 0, -3, + -3, -8, 0, -4, 0, -8, -3, 0, + -3, -7, 0, -4, -11, -8, -5, 0, + 0, 0, 0, 0, -3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -6, -32, -5, -3, -16, -19, 0, 0, + 0, 0, 0, 19, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -4, 1, + -2, 1, -3, -10, 1, 8, 1, 3, + -15, -5, -9, 0, -6, -15, -7, -10, + -16, -15, 0, -3, -3, -5, -3, 0, + -3, -1, 6, 0, 6, -3, 0, 12, + 0, 0, 0, 0, -3, -4, -4, 0, + 0, -10, 0, -2, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -4, -4, 0, -5, 0, 0, 4, -7, + -7, -3, 0, -11, -3, -8, -3, -5, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, -7, 0, 0, + 0, 0, -5, 0, -4, 0, 0, -2, + 0, 0, -13, 3, 4, 4, -1, -11, + 3, 6, 3, 12, -10, 0, -3, 0, + -3, -15, 0, 0, -12, -10, 0, -7, + 0, -6, 0, -6, 0, -3, 6, 0, + -3, -12, -4, 14, 0, 0, 0, -4, + 3, 0, 0, -13, 0, -3, -1, 0, + 0, 0, -3, 0, -3, -16, -5, -8, + 0, -12, 0, -4, 0, -7, 0, 2, + 0, -4, 0, -4, -12, 0, -4, 4, + 0, 0, 1, 0, -5, -3, 0, -5, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -3, 0, 0, 0, 0, 1, 0, + -4, -4, 0, 0, 9, 8, -24, 1, + 17, 12, 7, -15, 3, 16, 0, 14, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0 +}; + + +/*Collect the kern class' data in one place*/ +static const lv_font_fmt_txt_kern_classes_t kern_classes = +{ + .class_pair_values = kern_class_values, + .left_class_mapping = kern_left_class_mapping, + .right_class_mapping = kern_right_class_mapping, + .left_class_cnt = 46, + .right_class_cnt = 36, +}; + +/*-------------------- + * ALL CUSTOM DATA + *--------------------*/ + +#if LVGL_VERSION_MAJOR == 8 +/*Store all the custom data of the font*/ +static lv_font_fmt_txt_glyph_cache_t cache; +#endif + +#if LVGL_VERSION_MAJOR >= 8 +static const lv_font_fmt_txt_dsc_t font_dsc = { +#else +static lv_font_fmt_txt_dsc_t font_dsc = { +#endif + .glyph_bitmap = glyph_bitmap, + .glyph_dsc = glyph_dsc, + .cmaps = cmaps, + .kern_dsc = &kern_classes, + .kern_scale = 16, + .cmap_num = 4, + .bpp = 4, + .kern_classes = 1, + .bitmap_format = 0, +#if LVGL_VERSION_MAJOR == 8 + .cache = &cache +#endif +}; + + + +/*----------------- + * PUBLIC FONT + *----------------*/ + +/*Initialize a public general font descriptor*/ +#if LVGL_VERSION_MAJOR >= 8 +const lv_font_t montserrat_medium_24 = { +#else +lv_font_t montserrat_medium_24 = { +#endif + .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ + .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ + .line_height = 27, /*The maximum line height required by the font*/ + .base_line = 5, /*Baseline measured from the bottom of the line*/ +#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) + .subpx = LV_FONT_SUBPX_NONE, +#endif +#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 + .underline_position = -2, + .underline_thickness = 1, +#endif + .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ +#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 + .fallback = NULL, +#endif + .user_data = NULL, +}; + + + +#endif /*#if MONTSERRAT_MEDIUM_24*/ + diff --git a/main/fonts/notomedium16.c b/main/fonts/notomedium16.c index abe093e..56e237b 100644 --- a/main/fonts/notomedium16.c +++ b/main/fonts/notomedium16.c @@ -1,692 +1,692 @@ -/******************************************************************************* - * Size: 16 px - * Bpp: 1 - * Opts: --bpp 1 --size 16 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°éCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz --format lvgl -o notomedium16.c - ******************************************************************************/ - -#ifdef LV_LVGL_H_INCLUDE_SIMPLE -#include "lvgl.h" -#else -#include "lvgl/lvgl.h" -#endif - -#ifndef NOTOMEDIUM16 -#define NOTOMEDIUM16 1 -#endif - -#if NOTOMEDIUM16 - -/*----------------- - * BITMAPS - *----------------*/ - -/*Store the image of the glyphs*/ -static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { - /* U+002E "." */ - 0xf0, - - /* U+0030 "0" */ - 0x1c, 0x31, 0x98, 0xd8, 0x3c, 0x1e, 0xf, 0x7, - 0x83, 0xc1, 0xb1, 0x98, 0xc7, 0xc0, - - /* U+0031 "1" */ - 0xf8, 0xc6, 0x31, 0x8c, 0x63, 0x18, 0xc6, 0x30, - - /* U+0032 "2" */ - 0x7c, 0xc6, 0x3, 0x3, 0x3, 0x7, 0xe, 0x1c, - 0x38, 0x30, 0x60, 0xff, - - /* U+0033 "3" */ - 0x7f, 0x1, 0x81, 0x80, 0x80, 0xc0, 0xf0, 0x1c, - 0x3, 0x1, 0x80, 0xd0, 0xcf, 0xc0, - - /* U+0034 "4" */ - 0x6, 0x3, 0x80, 0xc0, 0x60, 0x30, 0xc, 0xc6, - 0x33, 0xc, 0xff, 0xc0, 0xc0, 0x30, 0xc, - - /* U+0035 "5" */ - 0x3f, 0x30, 0x18, 0xc, 0x6, 0x3, 0xf0, 0xc, - 0x3, 0x1, 0x80, 0xf0, 0xcf, 0xc0, - - /* U+0036 "6" */ - 0x1f, 0x18, 0x98, 0x18, 0xc, 0x6, 0xf3, 0x8d, - 0xc3, 0xc1, 0xb0, 0xd8, 0xc3, 0xc0, - - /* U+0037 "7" */ - 0xff, 0xe0, 0xb0, 0xc0, 0x40, 0x60, 0x30, 0x10, - 0x18, 0xc, 0x4, 0x6, 0x2, 0x0, - - /* U+0038 "8" */ - 0x3e, 0x71, 0xb0, 0x78, 0x36, 0x31, 0xf1, 0x8d, - 0x83, 0xc1, 0xe0, 0xd8, 0xc7, 0xc0, - - /* U+0039 "9" */ - 0x3c, 0x31, 0xb0, 0x58, 0x3c, 0x1b, 0x1c, 0xf6, - 0x3, 0x1, 0x81, 0x91, 0x8f, 0x80, - - /* U+0041 "A" */ - 0x6, 0x0, 0xe0, 0xf, 0x0, 0x90, 0x19, 0x81, - 0x18, 0x30, 0x83, 0xc, 0x7f, 0xc6, 0x6, 0x40, - 0x6c, 0x3, - - /* U+0042 "B" */ - 0xfe, 0x30, 0xcc, 0x1b, 0x6, 0xc1, 0xb0, 0xcf, - 0xf3, 0x6, 0xc0, 0xf0, 0x3c, 0x1f, 0xfc, - - /* U+0043 "C" */ - 0xf, 0x86, 0x19, 0x81, 0x70, 0xc, 0x1, 0x80, - 0x30, 0x6, 0x0, 0xe0, 0xc, 0x8, 0xc3, 0x7, - 0xc0, - - /* U+0044 "D" */ - 0xff, 0x18, 0x33, 0x3, 0x60, 0x3c, 0x7, 0x80, - 0xf0, 0x1e, 0x3, 0xc0, 0x78, 0x1b, 0x6, 0x7f, - 0x80, - - /* U+0045 "E" */ - 0xff, 0x60, 0x30, 0x18, 0xc, 0x6, 0x3, 0xfd, - 0x80, 0xc0, 0x60, 0x30, 0x1f, 0xf0, - - /* U+0046 "F" */ - 0xff, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xff, 0xc0, - 0xc0, 0xc0, 0xc0, 0xc0, - - /* U+0047 "G" */ - 0x1f, 0x8c, 0x36, 0x3, 0x0, 0xc0, 0x30, 0xc, - 0xf, 0x3, 0xc0, 0xd8, 0x33, 0xc, 0x7e, - - /* U+0048 "H" */ - 0xc0, 0xf0, 0x3c, 0xf, 0x3, 0xc0, 0xf0, 0x3f, - 0xff, 0x3, 0xc0, 0xf0, 0x3c, 0xf, 0x3, - - /* U+0049 "I" */ - 0xff, 0xff, 0xff, - - /* U+004A "J" */ - 0x7e, 0xc, 0x18, 0x30, 0x60, 0xc1, 0x83, 0x6, - 0xf, 0x33, 0xc0, - - /* U+004B "K" */ - 0xc0, 0xb0, 0x6c, 0x33, 0x18, 0xcc, 0x36, 0xf, - 0xc3, 0x98, 0xc7, 0x30, 0xcc, 0x1b, 0x3, - - /* U+004C "L" */ - 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, - 0xc0, 0xc0, 0xc0, 0xff, - - /* U+004D "M" */ - 0xc0, 0x3c, 0x3, 0xe0, 0x7e, 0x7, 0xd0, 0xbd, - 0x9b, 0xc9, 0x3c, 0xf3, 0xc6, 0x3c, 0x63, 0xc0, - 0x3c, 0x3, - - /* U+004E "N" */ - 0xc0, 0xf8, 0x3e, 0xf, 0xc3, 0xd8, 0xf3, 0x3c, - 0xcf, 0x1b, 0xc3, 0xf0, 0x7c, 0x1f, 0x3, - - /* U+004F "O" */ - 0xf, 0x83, 0xc, 0x60, 0x6c, 0x6, 0xc0, 0x3c, - 0x3, 0xc0, 0x3c, 0x3, 0xc0, 0x76, 0x6, 0x30, - 0xc1, 0xf8, - - /* U+0050 "P" */ - 0xfe, 0x61, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0xd, - 0xfc, 0xc0, 0x60, 0x30, 0x18, 0x0, - - /* U+0051 "Q" */ - 0xf, 0x83, 0xc, 0x60, 0x64, 0x6, 0xc0, 0x3c, - 0x3, 0xc0, 0x3c, 0x3, 0xc0, 0x76, 0x6, 0x30, - 0xc1, 0xf8, 0x3, 0x10, 0xf, - - /* U+0052 "R" */ - 0xfe, 0x61, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0xd, - 0xfc, 0xc6, 0x61, 0x30, 0xd8, 0x30, - - /* U+0053 "S" */ - 0x3f, 0x30, 0xb0, 0x18, 0xe, 0x3, 0xf0, 0xfc, - 0x7, 0x1, 0x80, 0xf0, 0xcf, 0xc0, - - /* U+0054 "T" */ - 0xff, 0x86, 0x3, 0x1, 0x80, 0xc0, 0x60, 0x30, - 0x18, 0xc, 0x6, 0x3, 0x1, 0x80, - - /* U+0055 "U" */ - 0xc0, 0xf0, 0x3c, 0xf, 0x3, 0xc0, 0xf0, 0x3c, - 0xf, 0x3, 0xc0, 0xd0, 0x26, 0x18, 0xfc, - - /* U+0056 "V" */ - 0xc0, 0x28, 0xd, 0x81, 0x30, 0x63, 0xc, 0x61, - 0x4, 0x60, 0xc8, 0x1b, 0x1, 0xe0, 0x38, 0x3, - 0x0, - - /* U+0057 "W" */ - 0x81, 0x81, 0x60, 0xc1, 0xb0, 0x70, 0xc8, 0x78, - 0x46, 0x24, 0x23, 0x13, 0x30, 0x99, 0x90, 0x48, - 0x48, 0x34, 0x2c, 0x1e, 0x1e, 0x6, 0x6, 0x3, - 0x3, 0x0, - - /* U+0058 "X" */ - 0x60, 0xcc, 0x10, 0xc6, 0xd, 0x80, 0xe0, 0x1c, - 0x3, 0x80, 0xd0, 0x13, 0x6, 0x31, 0x83, 0x20, - 0x60, - - /* U+0059 "Y" */ - 0xc0, 0x70, 0x36, 0x18, 0x84, 0x33, 0x6, 0x81, - 0xe0, 0x30, 0xc, 0x3, 0x0, 0xc0, 0x30, - - /* U+005A "Z" */ - 0xff, 0x81, 0xc0, 0xc0, 0xc0, 0xc0, 0x60, 0x60, - 0x60, 0x30, 0x30, 0x30, 0x1f, 0xf0, - - /* U+0061 "a" */ - 0x7c, 0x46, 0x3, 0x3, 0x7f, 0xc3, 0xc3, 0xc7, - 0x7b, - - /* U+0062 "b" */ - 0xc0, 0x60, 0x30, 0x1b, 0xce, 0x36, 0xf, 0x7, - 0x83, 0xc1, 0xe0, 0xf8, 0xdb, 0xc0, - - /* U+0063 "c" */ - 0x3e, 0x63, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0x63, - 0x1e, - - /* U+0064 "d" */ - 0x1, 0x80, 0xc0, 0x67, 0xb6, 0x3e, 0xf, 0x7, - 0x83, 0xc1, 0xe0, 0xd8, 0xe7, 0xb0, - - /* U+0065 "e" */ - 0x3c, 0x66, 0xc3, 0xc1, 0xff, 0xc0, 0xc0, 0x62, - 0x3e, - - /* U+0066 "f" */ - 0x3d, 0x86, 0x3e, 0x61, 0x86, 0x18, 0x61, 0x86, - 0x18, - - /* U+0067 "g" */ - 0x3d, 0xb1, 0xf0, 0x78, 0x3c, 0x1e, 0xf, 0x6, - 0xc7, 0x3d, 0x80, 0xd0, 0xcf, 0xc0, - - /* U+0068 "h" */ - 0xc0, 0xc0, 0xc0, 0xde, 0xe6, 0xc3, 0xc3, 0xc3, - 0xc3, 0xc3, 0xc3, 0xc3, - - /* U+0069 "i" */ - 0xf3, 0xff, 0xff, - - /* U+006A "j" */ - 0x18, 0xc0, 0x31, 0x8c, 0x63, 0x18, 0xc6, 0x31, - 0x8f, 0xc0, - - /* U+006B "k" */ - 0xc0, 0x60, 0x30, 0x18, 0x6c, 0x66, 0x63, 0x61, - 0xf8, 0xec, 0x63, 0x30, 0xd8, 0x20, - - /* U+006C "l" */ - 0xff, 0xff, 0xff, - - /* U+006D "m" */ - 0xde, 0xf3, 0x9e, 0x6c, 0x30, 0xf0, 0xc3, 0xc3, - 0xf, 0xc, 0x3c, 0x30, 0xf0, 0xc3, 0xc3, 0xc, - - /* U+006E "n" */ - 0xde, 0xe6, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, - 0xc3, - - /* U+006F "o" */ - 0x3e, 0x31, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0x6, - 0xc6, 0x3e, 0x0, - - /* U+0070 "p" */ - 0xde, 0x71, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0x7, - 0xc6, 0xde, 0x60, 0x30, 0x18, 0x0, - - /* U+0071 "q" */ - 0x3d, 0xb1, 0xf0, 0x78, 0x3c, 0x1e, 0xf, 0x6, - 0xc7, 0x3d, 0x80, 0xc0, 0x60, 0x30, - - /* U+0072 "r" */ - 0xdf, 0x31, 0x8c, 0x63, 0x18, 0xc0, - - /* U+0073 "s" */ - 0x7d, 0x8b, 0x7, 0x7, 0xc3, 0xc1, 0xc3, 0xfc, - - /* U+0074 "t" */ - 0x61, 0x8f, 0x98, 0x61, 0x86, 0x18, 0x61, 0x83, - 0xc0, - - /* U+0075 "u" */ - 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0x67, - 0x7b, - - /* U+0076 "v" */ - 0xc1, 0xa0, 0x98, 0xcc, 0x62, 0x21, 0xb0, 0x50, - 0x38, 0x18, 0x0, - - /* U+0077 "w" */ - 0xc3, 0x5, 0xc, 0x34, 0x38, 0x99, 0xa2, 0x24, - 0x98, 0x93, 0x43, 0xc5, 0x6, 0x1c, 0x18, 0x60, - - /* U+0078 "x" */ - 0x43, 0x31, 0xd, 0x83, 0x81, 0x80, 0xe0, 0xd8, - 0xc6, 0x43, 0x0, - - /* U+0079 "y" */ - 0xc1, 0xa0, 0x98, 0xcc, 0x42, 0x21, 0xb0, 0x50, - 0x38, 0x8, 0xc, 0x24, 0x1e, 0x0, - - /* U+007A "z" */ - 0xfe, 0xc, 0x30, 0xc1, 0x6, 0x18, 0x60, 0xfe, - - /* U+00B0 "°" */ - 0x76, 0xe3, 0x1d, 0xb8, - - /* U+00E9 "é" */ - 0xc, 0x18, 0x0, 0x3c, 0x66, 0xc3, 0xc1, 0xff, - 0xc0, 0xc0, 0x62, 0x3e -}; - - -/*--------------------- - * GLYPH DESCRIPTION - *--------------------*/ - -static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { - {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, - {.bitmap_index = 0, .adv_w = 58, .box_w = 2, .box_h = 2, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 1, .adv_w = 171, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 15, .adv_w = 95, .box_w = 5, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 23, .adv_w = 147, .box_w = 8, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 35, .adv_w = 146, .box_w = 9, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 49, .adv_w = 171, .box_w = 10, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 64, .adv_w = 147, .box_w = 9, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 78, .adv_w = 158, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 92, .adv_w = 153, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 106, .adv_w = 165, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 120, .adv_w = 158, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 134, .adv_w = 187, .box_w = 12, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 152, .adv_w = 194, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 167, .adv_w = 185, .box_w = 11, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 184, .adv_w = 211, .box_w = 11, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 201, .adv_w = 172, .box_w = 9, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 215, .adv_w = 163, .box_w = 8, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 227, .adv_w = 198, .box_w = 10, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 242, .adv_w = 208, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 257, .adv_w = 79, .box_w = 2, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 260, .adv_w = 131, .box_w = 7, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 271, .adv_w = 184, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 286, .adv_w = 152, .box_w = 8, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 298, .adv_w = 244, .box_w = 12, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 316, .adv_w = 208, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 331, .adv_w = 215, .box_w = 12, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 349, .adv_w = 185, .box_w = 9, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 363, .adv_w = 215, .box_w = 12, .box_h = 14, .ofs_x = 1, .ofs_y = -2}, - {.bitmap_index = 384, .adv_w = 186, .box_w = 9, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 398, .adv_w = 159, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 412, .adv_w = 150, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 426, .adv_w = 202, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, - {.bitmap_index = 441, .adv_w = 182, .box_w = 11, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 458, .adv_w = 288, .box_w = 17, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 484, .adv_w = 172, .box_w = 11, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 501, .adv_w = 166, .box_w = 10, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 516, .adv_w = 168, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 530, .adv_w = 153, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 539, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 553, .adv_w = 146, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 562, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 576, .adv_w = 157, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 585, .adv_w = 90, .box_w = 6, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 594, .adv_w = 177, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = -3}, - {.bitmap_index = 608, .adv_w = 174, .box_w = 8, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 620, .adv_w = 71, .box_w = 2, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 623, .adv_w = 73, .box_w = 5, .box_h = 15, .ofs_x = -2, .ofs_y = -3}, - {.bitmap_index = 633, .adv_w = 158, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 647, .adv_w = 71, .box_w = 2, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 650, .adv_w = 271, .box_w = 14, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 666, .adv_w = 174, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 675, .adv_w = 163, .box_w = 9, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 686, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = -3}, - {.bitmap_index = 700, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = -3}, - {.bitmap_index = 714, .adv_w = 105, .box_w = 5, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 720, .adv_w = 128, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 728, .adv_w = 106, .box_w = 6, .box_h = 11, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 737, .adv_w = 173, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 746, .adv_w = 143, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 757, .adv_w = 230, .box_w = 14, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 773, .adv_w = 141, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, - {.bitmap_index = 784, .adv_w = 143, .box_w = 9, .box_h = 12, .ofs_x = 0, .ofs_y = -3}, - {.bitmap_index = 798, .adv_w = 133, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, - {.bitmap_index = 806, .adv_w = 107, .box_w = 5, .box_h = 6, .ofs_x = 1, .ofs_y = 6}, - {.bitmap_index = 810, .adv_w = 157, .box_w = 8, .box_h = 12, .ofs_x = 1, .ofs_y = 0} -}; - -/*--------------------- - * CHARACTER MAPPING - *--------------------*/ - -static const uint8_t glyph_id_ofs_list_0[] = { - 0, 0, 1, 2, 3, 4, 5, 6, - 7, 8, 9, 10 -}; - -static const uint16_t unicode_list_3[] = { - 0x0, 0x39 -}; - -/*Collect the unicode lists and glyph_id offsets*/ -static const lv_font_fmt_txt_cmap_t cmaps[] = -{ - { - .range_start = 46, .range_length = 12, .glyph_id_start = 1, - .unicode_list = NULL, .glyph_id_ofs_list = glyph_id_ofs_list_0, .list_length = 12, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_FULL - }, - { - .range_start = 65, .range_length = 26, .glyph_id_start = 12, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 97, .range_length = 26, .glyph_id_start = 38, - .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY - }, - { - .range_start = 176, .range_length = 58, .glyph_id_start = 64, - .unicode_list = unicode_list_3, .glyph_id_ofs_list = NULL, .list_length = 2, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY - } -}; - -/*----------------- - * KERNING - *----------------*/ - - -/*Map glyph_ids to kern left classes*/ -static const uint8_t kern_left_class_mapping[] = -{ - 0, 1, 2, 0, 3, 4, 5, 6, - 7, 8, 9, 2, 10, 11, 12, 13, - 14, 15, 16, 17, 17, 18, 19, 20, - 17, 17, 13, 21, 13, 22, 23, 24, - 18, 25, 25, 26, 27, 28, 29, 30, - 31, 32, 33, 34, 35, 29, 35, 35, - 36, 32, 29, 29, 30, 30, 37, 38, - 39, 40, 35, 41, 41, 42, 41, 43, - 44, 33 -}; - -/*Map glyph_ids to kern right classes*/ -static const uint8_t kern_right_class_mapping[] = -{ - 0, 1, 2, 3, 4, 5, 6, 7, - 2, 8, 9, 10, 11, 12, 13, 12, - 12, 12, 13, 12, 12, 14, 12, 12, - 12, 12, 13, 12, 13, 12, 15, 16, - 17, 18, 18, 19, 20, 21, 22, 23, - 24, 24, 24, 0, 24, 23, 25, 26, - 23, 23, 27, 27, 24, 27, 24, 27, - 28, 29, 30, 31, 31, 32, 31, 33, - 34, 24 -}; - -/*Kern values between classes*/ -static const int8_t kern_class_values[] = -{ - 0, -3, -3, 3, 3, -2, 0, -3, - 3, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -16, -3, 0, -1, -1, -3, 0, - 0, -2, 0, 0, -2, 0, 0, -6, - 0, -5, 0, -6, -8, -8, -5, 0, - 0, 0, 0, -2, 0, 0, 3, 0, - 2, -3, 0, 1, 3, -1, 0, 0, - 0, -5, 0, -1, 0, 0, 1, 0, - 0, 3, 0, -2, 0, -3, 0, -4, - 0, 0, 0, -3, 0, 0, 0, 0, - 0, -1, 1, -2, -2, 0, 0, 0, - 0, -1, -1, 0, -3, -3, 0, 0, - 1, 0, 0, 0, 0, -2, 0, -3, - -3, -3, 0, 0, 0, 0, 0, -2, - 0, 0, 0, 0, -2, -3, 0, -4, - 5, 0, -6, -1, -3, 0, -1, -12, - 3, -2, 0, 0, 3, 1, -2, -13, - 0, -14, -2, -22, -2, 7, 0, 3, - 0, 0, 0, 0, 1, 0, -5, -3, - 0, -8, 0, 0, 0, -1, -1, 0, - -1, -3, 0, 0, 0, 0, 0, -3, - 0, -3, 0, -2, -3, -2, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - -2, -2, 0, -3, 3, 0, 0, 0, - 0, 0, 0, -2, 0, 0, 2, 0, - 0, 0, 0, -3, 0, -3, -2, -3, - 0, 0, 0, 2, 0, -2, 0, 0, - 0, 0, -3, -4, 0, -5, -13, -5, - 3, 0, -2, -17, -5, 0, -5, 0, - -16, 0, -5, -7, -2, 0, 0, 1, - -1, 2, -2, -10, 0, -13, -6, -5, - -6, -8, -3, -7, -1, -5, -7, 2, - 3, 0, 0, 0, 0, 0, 0, 0, - 0, 0, -1, 0, 0, -1, 0, -3, - 0, -4, -6, -6, -1, 0, 0, 0, - 0, -2, 0, 0, 0, 0, 1, -2, - 0, 0, 8, -2, -11, 0, 3, -4, - 0, -13, -1, -3, 3, 0, -3, 4, - 0, -9, -4, -9, -8, -11, 0, 0, - 0, -1, 0, 0, 0, -1, -1, -3, - -7, -8, -1, -24, 1, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, -3, 0, -1, -3, -4, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 3, -6, - 3, -2, -1, -7, -3, 0, -3, -3, - -4, 0, -4, 0, -1, -2, -1, -2, - -4, -3, 0, -2, 0, -6, 0, 0, - 0, -5, 0, -4, 0, -4, -4, 3, - -5, 0, -3, -3, -3, 0, 0, 0, - 0, 0, -3, 0, 0, -4, 0, -3, - 0, -6, -6, -8, -2, 0, 0, 0, - 0, 20, 0, 0, 1, 0, 0, -3, - 0, 3, 3, -4, 0, -2, -3, -8, - -2, -2, -2, -1, 0, 0, -1, 0, - 0, 0, 0, -3, -2, -2, 0, -2, - 0, -2, 0, 0, 0, -2, -3, -2, - -2, -3, -2, 0, -3, -3, 4, 0, - 0, -12, -4, 3, -4, 2, -8, 0, - -2, -4, -1, 1, 0, 0, -4, 0, - 0, -5, 0, -4, -3, -4, -3, -3, - 0, -4, 1, -5, -4, 8, 3, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, -2, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, -2, 0, 0, 0, 0, 0, - 0, 0, 0, 0, -4, 0, 0, 0, - 0, -3, 0, 0, -3, -3, 0, 0, - 0, 0, 0, -1, 0, 0, 0, 0, - 0, -2, 0, 0, 0, -6, 5, 1, - -2, -12, 0, 0, -6, -3, -7, 0, - -6, 0, -4, -11, -3, -10, -10, -12, - 0, -3, 0, -6, -3, -1, -3, -4, - -7, -5, -9, -10, -6, -3, 8, -6, - -9, 0, 1, -8, 0, -13, -2, -3, - 1, 0, -3, 0, -2, -17, -3, -13, - -3, -19, 0, 1, 0, -2, 0, 0, - 0, 0, -1, -2, -10, -2, 0, -17, - -7, 0, 0, -1, -4, -8, -3, 0, - -2, 0, -12, -3, 0, -8, 0, -8, - -2, -4, -6, -3, -4, -4, 0, -3, - -5, -3, -5, 0, 1, 0, -2, -8, - 0, 5, 0, 0, 0, 0, -2, -5, - 0, 0, 0, 0, 0, 0, 0, -3, - 0, -3, 0, 0, -5, -3, 0, -1, - 0, 0, 0, 0, 0, 0, 1, 0, - 0, 0, 0, 4, 5, 0, -3, 0, - -2, 3, 0, -3, 0, -3, 0, 0, - 0, 0, 0, -3, 0, 0, -3, -4, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, -3, -3, 0, -4, -8, -5, - 10, 5, 3, -22, -2, 5, -3, 0, - -9, 0, -3, -3, -2, 3, -3, -2, - -8, -2, 0, -7, 0, -14, -3, 7, - -3, -10, 1, -3, -8, -8, -3, 10, - -9, -6, 8, 0, 1, -19, -2, 3, - -4, -2, -9, -4, -6, -4, -4, -2, - 0, 0, -6, -5, -3, -14, 0, -14, - -4, 0, -9, -15, -1, -8, -4, -8, - -7, 7, 0, -8, 3, 0, 0, -14, - 0, -3, -6, -4, -8, -6, -6, 0, - -3, -8, -3, -6, -5, -8, -3, -4, - 0, -8, -3, 0, -3, -5, -6, -7, - -7, -10, -3, -5, -9, -8, 8, -3, - 1, -24, -5, 5, -6, -4, -11, -3, - -8, -3, -4, -2, -3, -5, -8, -1, - 0, -17, 0, -15, -6, 6, -10, -17, - -5, -9, -11, -13, -8, 5, 5, -5, - 5, 0, 0, -8, -1, 0, -1, 0, - 0, 0, -2, 0, 0, 0, 0, 0, - -3, 0, 0, 1, 0, -3, 0, 0, - 0, 0, -2, -2, -3, 0, 0, 0, - 0, 0, -6, -1, 0, 0, 0, -6, - 0, -3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 1, - 0, 0, 0, 0, 0, 0, -3, 0, - 0, -5, -3, 0, -7, -3, -6, 0, - 0, -7, 0, -3, -3, 0, 0, 0, - 0, -21, -5, -10, -3, -9, 0, -1, - 0, 0, 0, 0, 0, 0, 0, 0, - -4, -5, -2, -4, 5, -2, -6, -2, - -4, -5, 0, -3, -1, -2, 0, 0, - -1, 0, 0, -23, -2, -4, 0, -6, - 0, 0, -2, -2, 0, 0, 0, 0, - 2, 0, -2, -4, -2, 4, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 3, 0, 0, 0, 0, 0, - 0, 0, -7, -3, -5, 0, 0, -7, - 0, -3, 0, 0, 0, 0, 0, -25, - 0, -5, -9, -13, 0, -4, 0, 0, - 0, 0, 0, 0, 0, 0, -3, -4, - -1, -4, -3, 3, 13, 4, 6, -7, - 3, 11, 3, 7, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, -3, - 0, -2, 20, 11, 20, 0, 0, 0, - 3, 0, 0, 9, 0, 0, -2, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, -4, -22, -3, -2, -10, -13, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 3, -3, - 2, 5, 3, -8, 0, -1, -2, 3, - 0, 0, 0, 0, 0, -6, 0, -2, - -2, -5, 0, -3, 0, -6, -2, 0, - -2, -4, 0, -3, -7, -5, -3, 0, - 0, 0, -2, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -4, -22, - -3, -2, -10, -13, 0, 0, 0, 0, - 0, 13, 0, 0, 0, 0, 0, 0, - 0, 0, -3, 1, -2, 1, -2, -7, - 1, 6, 1, 2, -10, -3, -6, 0, - -4, -10, -5, -7, -11, -10, 0, -2, - -2, -3, -2, 0, -2, -1, 4, 0, - 4, -2, 0, 8, 0, 0, -2, -3, - -3, 0, 0, -7, 0, -1, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, -3, -3, 0, -3, 3, -4, - -5, -2, 0, -7, -2, -6, -2, -3, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -5, 0, 0, - 0, 0, -3, 0, -3, 0, 0, -1, - -8, 2, 3, 3, -1, -7, 2, 4, - 2, 8, -7, 0, -2, 0, -2, -10, - 0, 0, -8, -7, 0, -4, 0, -4, - 0, -4, 0, -2, 4, 0, -2, -8, - -3, 9, 0, -3, 2, 0, 0, -8, - 0, -2, -1, 0, 0, 0, -2, 0, - -2, -10, -3, -6, 0, -8, 0, -3, - 0, -5, 0, 2, 0, -3, 0, -3, - -8, 0, -3, 3, 1, 0, -3, -2, - 0, -3, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, -2, 0, 0, 0, 0, - 1, 0, -3, -3, 0, 0, -16, 1, - 11, 8, 4, -10, 2, 11, 0, 9, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0 -}; - - -/*Collect the kern class' data in one place*/ -static const lv_font_fmt_txt_kern_classes_t kern_classes = -{ - .class_pair_values = kern_class_values, - .left_class_mapping = kern_left_class_mapping, - .right_class_mapping = kern_right_class_mapping, - .left_class_cnt = 44, - .right_class_cnt = 34, -}; - -/*-------------------- - * ALL CUSTOM DATA - *--------------------*/ - -#if LVGL_VERSION_MAJOR == 8 -/*Store all the custom data of the font*/ -static lv_font_fmt_txt_glyph_cache_t cache; -#endif - -#if LVGL_VERSION_MAJOR >= 8 -static const lv_font_fmt_txt_dsc_t font_dsc = { -#else -static lv_font_fmt_txt_dsc_t font_dsc = { -#endif - .glyph_bitmap = glyph_bitmap, - .glyph_dsc = glyph_dsc, - .cmaps = cmaps, - .kern_dsc = &kern_classes, - .kern_scale = 16, - .cmap_num = 4, - .bpp = 1, - .kern_classes = 1, - .bitmap_format = 0, -#if LVGL_VERSION_MAJOR == 8 - .cache = &cache -#endif -}; - - - -/*----------------- - * PUBLIC FONT - *----------------*/ - -/*Initialize a public general font descriptor*/ -#if LVGL_VERSION_MAJOR >= 8 -const lv_font_t notomedium16 = { -#else -lv_font_t notomedium16 = { -#endif - .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ - .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ - .line_height = 15, /*The maximum line height required by the font*/ - .base_line = 3, /*Baseline measured from the bottom of the line*/ -#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) - .subpx = LV_FONT_SUBPX_NONE, -#endif -#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 - .underline_position = -1, - .underline_thickness = 1, -#endif - .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ -#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 - .fallback = NULL, -#endif - .user_data = NULL, -}; - - - -#endif /*#if NOTOMEDIUM16*/ - +/******************************************************************************* + * Size: 16 px + * Bpp: 1 + * Opts: --bpp 1 --size 16 --no-compress --font Montserrat-Medium.ttf --symbols 0123456789.°éCABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz --format lvgl -o notomedium16.c + ******************************************************************************/ + +#ifdef LV_LVGL_H_INCLUDE_SIMPLE +#include "lvgl.h" +#else +#include "lvgl/lvgl.h" +#endif + +#ifndef NOTOMEDIUM16 +#define NOTOMEDIUM16 1 +#endif + +#if NOTOMEDIUM16 + +/*----------------- + * BITMAPS + *----------------*/ + +/*Store the image of the glyphs*/ +static LV_ATTRIBUTE_LARGE_CONST const uint8_t glyph_bitmap[] = { + /* U+002E "." */ + 0xf0, + + /* U+0030 "0" */ + 0x1c, 0x31, 0x98, 0xd8, 0x3c, 0x1e, 0xf, 0x7, + 0x83, 0xc1, 0xb1, 0x98, 0xc7, 0xc0, + + /* U+0031 "1" */ + 0xf8, 0xc6, 0x31, 0x8c, 0x63, 0x18, 0xc6, 0x30, + + /* U+0032 "2" */ + 0x7c, 0xc6, 0x3, 0x3, 0x3, 0x7, 0xe, 0x1c, + 0x38, 0x30, 0x60, 0xff, + + /* U+0033 "3" */ + 0x7f, 0x1, 0x81, 0x80, 0x80, 0xc0, 0xf0, 0x1c, + 0x3, 0x1, 0x80, 0xd0, 0xcf, 0xc0, + + /* U+0034 "4" */ + 0x6, 0x3, 0x80, 0xc0, 0x60, 0x30, 0xc, 0xc6, + 0x33, 0xc, 0xff, 0xc0, 0xc0, 0x30, 0xc, + + /* U+0035 "5" */ + 0x3f, 0x30, 0x18, 0xc, 0x6, 0x3, 0xf0, 0xc, + 0x3, 0x1, 0x80, 0xf0, 0xcf, 0xc0, + + /* U+0036 "6" */ + 0x1f, 0x18, 0x98, 0x18, 0xc, 0x6, 0xf3, 0x8d, + 0xc3, 0xc1, 0xb0, 0xd8, 0xc3, 0xc0, + + /* U+0037 "7" */ + 0xff, 0xe0, 0xb0, 0xc0, 0x40, 0x60, 0x30, 0x10, + 0x18, 0xc, 0x4, 0x6, 0x2, 0x0, + + /* U+0038 "8" */ + 0x3e, 0x71, 0xb0, 0x78, 0x36, 0x31, 0xf1, 0x8d, + 0x83, 0xc1, 0xe0, 0xd8, 0xc7, 0xc0, + + /* U+0039 "9" */ + 0x3c, 0x31, 0xb0, 0x58, 0x3c, 0x1b, 0x1c, 0xf6, + 0x3, 0x1, 0x81, 0x91, 0x8f, 0x80, + + /* U+0041 "A" */ + 0x6, 0x0, 0xe0, 0xf, 0x0, 0x90, 0x19, 0x81, + 0x18, 0x30, 0x83, 0xc, 0x7f, 0xc6, 0x6, 0x40, + 0x6c, 0x3, + + /* U+0042 "B" */ + 0xfe, 0x30, 0xcc, 0x1b, 0x6, 0xc1, 0xb0, 0xcf, + 0xf3, 0x6, 0xc0, 0xf0, 0x3c, 0x1f, 0xfc, + + /* U+0043 "C" */ + 0xf, 0x86, 0x19, 0x81, 0x70, 0xc, 0x1, 0x80, + 0x30, 0x6, 0x0, 0xe0, 0xc, 0x8, 0xc3, 0x7, + 0xc0, + + /* U+0044 "D" */ + 0xff, 0x18, 0x33, 0x3, 0x60, 0x3c, 0x7, 0x80, + 0xf0, 0x1e, 0x3, 0xc0, 0x78, 0x1b, 0x6, 0x7f, + 0x80, + + /* U+0045 "E" */ + 0xff, 0x60, 0x30, 0x18, 0xc, 0x6, 0x3, 0xfd, + 0x80, 0xc0, 0x60, 0x30, 0x1f, 0xf0, + + /* U+0046 "F" */ + 0xff, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xff, 0xc0, + 0xc0, 0xc0, 0xc0, 0xc0, + + /* U+0047 "G" */ + 0x1f, 0x8c, 0x36, 0x3, 0x0, 0xc0, 0x30, 0xc, + 0xf, 0x3, 0xc0, 0xd8, 0x33, 0xc, 0x7e, + + /* U+0048 "H" */ + 0xc0, 0xf0, 0x3c, 0xf, 0x3, 0xc0, 0xf0, 0x3f, + 0xff, 0x3, 0xc0, 0xf0, 0x3c, 0xf, 0x3, + + /* U+0049 "I" */ + 0xff, 0xff, 0xff, + + /* U+004A "J" */ + 0x7e, 0xc, 0x18, 0x30, 0x60, 0xc1, 0x83, 0x6, + 0xf, 0x33, 0xc0, + + /* U+004B "K" */ + 0xc0, 0xb0, 0x6c, 0x33, 0x18, 0xcc, 0x36, 0xf, + 0xc3, 0x98, 0xc7, 0x30, 0xcc, 0x1b, 0x3, + + /* U+004C "L" */ + 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, + 0xc0, 0xc0, 0xc0, 0xff, + + /* U+004D "M" */ + 0xc0, 0x3c, 0x3, 0xe0, 0x7e, 0x7, 0xd0, 0xbd, + 0x9b, 0xc9, 0x3c, 0xf3, 0xc6, 0x3c, 0x63, 0xc0, + 0x3c, 0x3, + + /* U+004E "N" */ + 0xc0, 0xf8, 0x3e, 0xf, 0xc3, 0xd8, 0xf3, 0x3c, + 0xcf, 0x1b, 0xc3, 0xf0, 0x7c, 0x1f, 0x3, + + /* U+004F "O" */ + 0xf, 0x83, 0xc, 0x60, 0x6c, 0x6, 0xc0, 0x3c, + 0x3, 0xc0, 0x3c, 0x3, 0xc0, 0x76, 0x6, 0x30, + 0xc1, 0xf8, + + /* U+0050 "P" */ + 0xfe, 0x61, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0xd, + 0xfc, 0xc0, 0x60, 0x30, 0x18, 0x0, + + /* U+0051 "Q" */ + 0xf, 0x83, 0xc, 0x60, 0x64, 0x6, 0xc0, 0x3c, + 0x3, 0xc0, 0x3c, 0x3, 0xc0, 0x76, 0x6, 0x30, + 0xc1, 0xf8, 0x3, 0x10, 0xf, + + /* U+0052 "R" */ + 0xfe, 0x61, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0xd, + 0xfc, 0xc6, 0x61, 0x30, 0xd8, 0x30, + + /* U+0053 "S" */ + 0x3f, 0x30, 0xb0, 0x18, 0xe, 0x3, 0xf0, 0xfc, + 0x7, 0x1, 0x80, 0xf0, 0xcf, 0xc0, + + /* U+0054 "T" */ + 0xff, 0x86, 0x3, 0x1, 0x80, 0xc0, 0x60, 0x30, + 0x18, 0xc, 0x6, 0x3, 0x1, 0x80, + + /* U+0055 "U" */ + 0xc0, 0xf0, 0x3c, 0xf, 0x3, 0xc0, 0xf0, 0x3c, + 0xf, 0x3, 0xc0, 0xd0, 0x26, 0x18, 0xfc, + + /* U+0056 "V" */ + 0xc0, 0x28, 0xd, 0x81, 0x30, 0x63, 0xc, 0x61, + 0x4, 0x60, 0xc8, 0x1b, 0x1, 0xe0, 0x38, 0x3, + 0x0, + + /* U+0057 "W" */ + 0x81, 0x81, 0x60, 0xc1, 0xb0, 0x70, 0xc8, 0x78, + 0x46, 0x24, 0x23, 0x13, 0x30, 0x99, 0x90, 0x48, + 0x48, 0x34, 0x2c, 0x1e, 0x1e, 0x6, 0x6, 0x3, + 0x3, 0x0, + + /* U+0058 "X" */ + 0x60, 0xcc, 0x10, 0xc6, 0xd, 0x80, 0xe0, 0x1c, + 0x3, 0x80, 0xd0, 0x13, 0x6, 0x31, 0x83, 0x20, + 0x60, + + /* U+0059 "Y" */ + 0xc0, 0x70, 0x36, 0x18, 0x84, 0x33, 0x6, 0x81, + 0xe0, 0x30, 0xc, 0x3, 0x0, 0xc0, 0x30, + + /* U+005A "Z" */ + 0xff, 0x81, 0xc0, 0xc0, 0xc0, 0xc0, 0x60, 0x60, + 0x60, 0x30, 0x30, 0x30, 0x1f, 0xf0, + + /* U+0061 "a" */ + 0x7c, 0x46, 0x3, 0x3, 0x7f, 0xc3, 0xc3, 0xc7, + 0x7b, + + /* U+0062 "b" */ + 0xc0, 0x60, 0x30, 0x1b, 0xce, 0x36, 0xf, 0x7, + 0x83, 0xc1, 0xe0, 0xf8, 0xdb, 0xc0, + + /* U+0063 "c" */ + 0x3e, 0x63, 0xc0, 0xc0, 0xc0, 0xc0, 0xc0, 0x63, + 0x1e, + + /* U+0064 "d" */ + 0x1, 0x80, 0xc0, 0x67, 0xb6, 0x3e, 0xf, 0x7, + 0x83, 0xc1, 0xe0, 0xd8, 0xe7, 0xb0, + + /* U+0065 "e" */ + 0x3c, 0x66, 0xc3, 0xc1, 0xff, 0xc0, 0xc0, 0x62, + 0x3e, + + /* U+0066 "f" */ + 0x3d, 0x86, 0x3e, 0x61, 0x86, 0x18, 0x61, 0x86, + 0x18, + + /* U+0067 "g" */ + 0x3d, 0xb1, 0xf0, 0x78, 0x3c, 0x1e, 0xf, 0x6, + 0xc7, 0x3d, 0x80, 0xd0, 0xcf, 0xc0, + + /* U+0068 "h" */ + 0xc0, 0xc0, 0xc0, 0xde, 0xe6, 0xc3, 0xc3, 0xc3, + 0xc3, 0xc3, 0xc3, 0xc3, + + /* U+0069 "i" */ + 0xf3, 0xff, 0xff, + + /* U+006A "j" */ + 0x18, 0xc0, 0x31, 0x8c, 0x63, 0x18, 0xc6, 0x31, + 0x8f, 0xc0, + + /* U+006B "k" */ + 0xc0, 0x60, 0x30, 0x18, 0x6c, 0x66, 0x63, 0x61, + 0xf8, 0xec, 0x63, 0x30, 0xd8, 0x20, + + /* U+006C "l" */ + 0xff, 0xff, 0xff, + + /* U+006D "m" */ + 0xde, 0xf3, 0x9e, 0x6c, 0x30, 0xf0, 0xc3, 0xc3, + 0xf, 0xc, 0x3c, 0x30, 0xf0, 0xc3, 0xc3, 0xc, + + /* U+006E "n" */ + 0xde, 0xe6, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, + 0xc3, + + /* U+006F "o" */ + 0x3e, 0x31, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0x6, + 0xc6, 0x3e, 0x0, + + /* U+0070 "p" */ + 0xde, 0x71, 0xb0, 0x78, 0x3c, 0x1e, 0xf, 0x7, + 0xc6, 0xde, 0x60, 0x30, 0x18, 0x0, + + /* U+0071 "q" */ + 0x3d, 0xb1, 0xf0, 0x78, 0x3c, 0x1e, 0xf, 0x6, + 0xc7, 0x3d, 0x80, 0xc0, 0x60, 0x30, + + /* U+0072 "r" */ + 0xdf, 0x31, 0x8c, 0x63, 0x18, 0xc0, + + /* U+0073 "s" */ + 0x7d, 0x8b, 0x7, 0x7, 0xc3, 0xc1, 0xc3, 0xfc, + + /* U+0074 "t" */ + 0x61, 0x8f, 0x98, 0x61, 0x86, 0x18, 0x61, 0x83, + 0xc0, + + /* U+0075 "u" */ + 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0xc3, 0x67, + 0x7b, + + /* U+0076 "v" */ + 0xc1, 0xa0, 0x98, 0xcc, 0x62, 0x21, 0xb0, 0x50, + 0x38, 0x18, 0x0, + + /* U+0077 "w" */ + 0xc3, 0x5, 0xc, 0x34, 0x38, 0x99, 0xa2, 0x24, + 0x98, 0x93, 0x43, 0xc5, 0x6, 0x1c, 0x18, 0x60, + + /* U+0078 "x" */ + 0x43, 0x31, 0xd, 0x83, 0x81, 0x80, 0xe0, 0xd8, + 0xc6, 0x43, 0x0, + + /* U+0079 "y" */ + 0xc1, 0xa0, 0x98, 0xcc, 0x42, 0x21, 0xb0, 0x50, + 0x38, 0x8, 0xc, 0x24, 0x1e, 0x0, + + /* U+007A "z" */ + 0xfe, 0xc, 0x30, 0xc1, 0x6, 0x18, 0x60, 0xfe, + + /* U+00B0 "°" */ + 0x76, 0xe3, 0x1d, 0xb8, + + /* U+00E9 "é" */ + 0xc, 0x18, 0x0, 0x3c, 0x66, 0xc3, 0xc1, 0xff, + 0xc0, 0xc0, 0x62, 0x3e +}; + + +/*--------------------- + * GLYPH DESCRIPTION + *--------------------*/ + +static const lv_font_fmt_txt_glyph_dsc_t glyph_dsc[] = { + {.bitmap_index = 0, .adv_w = 0, .box_w = 0, .box_h = 0, .ofs_x = 0, .ofs_y = 0} /* id = 0 reserved */, + {.bitmap_index = 0, .adv_w = 58, .box_w = 2, .box_h = 2, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 1, .adv_w = 171, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 15, .adv_w = 95, .box_w = 5, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 23, .adv_w = 147, .box_w = 8, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 35, .adv_w = 146, .box_w = 9, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 49, .adv_w = 171, .box_w = 10, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 64, .adv_w = 147, .box_w = 9, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 78, .adv_w = 158, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 92, .adv_w = 153, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 106, .adv_w = 165, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 120, .adv_w = 158, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 134, .adv_w = 187, .box_w = 12, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 152, .adv_w = 194, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 167, .adv_w = 185, .box_w = 11, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 184, .adv_w = 211, .box_w = 11, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 201, .adv_w = 172, .box_w = 9, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 215, .adv_w = 163, .box_w = 8, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 227, .adv_w = 198, .box_w = 10, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 242, .adv_w = 208, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 257, .adv_w = 79, .box_w = 2, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 260, .adv_w = 131, .box_w = 7, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 271, .adv_w = 184, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 286, .adv_w = 152, .box_w = 8, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 298, .adv_w = 244, .box_w = 12, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 316, .adv_w = 208, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 331, .adv_w = 215, .box_w = 12, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 349, .adv_w = 185, .box_w = 9, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 363, .adv_w = 215, .box_w = 12, .box_h = 14, .ofs_x = 1, .ofs_y = -2}, + {.bitmap_index = 384, .adv_w = 186, .box_w = 9, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 398, .adv_w = 159, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 412, .adv_w = 150, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 426, .adv_w = 202, .box_w = 10, .box_h = 12, .ofs_x = 2, .ofs_y = 0}, + {.bitmap_index = 441, .adv_w = 182, .box_w = 11, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 458, .adv_w = 288, .box_w = 17, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 484, .adv_w = 172, .box_w = 11, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 501, .adv_w = 166, .box_w = 10, .box_h = 12, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 516, .adv_w = 168, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 530, .adv_w = 153, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 539, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 553, .adv_w = 146, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 562, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 576, .adv_w = 157, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 585, .adv_w = 90, .box_w = 6, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 594, .adv_w = 177, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = -3}, + {.bitmap_index = 608, .adv_w = 174, .box_w = 8, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 620, .adv_w = 71, .box_w = 2, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 623, .adv_w = 73, .box_w = 5, .box_h = 15, .ofs_x = -2, .ofs_y = -3}, + {.bitmap_index = 633, .adv_w = 158, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 647, .adv_w = 71, .box_w = 2, .box_h = 12, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 650, .adv_w = 271, .box_w = 14, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 666, .adv_w = 174, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 675, .adv_w = 163, .box_w = 9, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 686, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = -3}, + {.bitmap_index = 700, .adv_w = 175, .box_w = 9, .box_h = 12, .ofs_x = 1, .ofs_y = -3}, + {.bitmap_index = 714, .adv_w = 105, .box_w = 5, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 720, .adv_w = 128, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 728, .adv_w = 106, .box_w = 6, .box_h = 11, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 737, .adv_w = 173, .box_w = 8, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 746, .adv_w = 143, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 757, .adv_w = 230, .box_w = 14, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 773, .adv_w = 141, .box_w = 9, .box_h = 9, .ofs_x = 0, .ofs_y = 0}, + {.bitmap_index = 784, .adv_w = 143, .box_w = 9, .box_h = 12, .ofs_x = 0, .ofs_y = -3}, + {.bitmap_index = 798, .adv_w = 133, .box_w = 7, .box_h = 9, .ofs_x = 1, .ofs_y = 0}, + {.bitmap_index = 806, .adv_w = 107, .box_w = 5, .box_h = 6, .ofs_x = 1, .ofs_y = 6}, + {.bitmap_index = 810, .adv_w = 157, .box_w = 8, .box_h = 12, .ofs_x = 1, .ofs_y = 0} +}; + +/*--------------------- + * CHARACTER MAPPING + *--------------------*/ + +static const uint8_t glyph_id_ofs_list_0[] = { + 0, 0, 1, 2, 3, 4, 5, 6, + 7, 8, 9, 10 +}; + +static const uint16_t unicode_list_3[] = { + 0x0, 0x39 +}; + +/*Collect the unicode lists and glyph_id offsets*/ +static const lv_font_fmt_txt_cmap_t cmaps[] = +{ + { + .range_start = 46, .range_length = 12, .glyph_id_start = 1, + .unicode_list = NULL, .glyph_id_ofs_list = glyph_id_ofs_list_0, .list_length = 12, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_FULL + }, + { + .range_start = 65, .range_length = 26, .glyph_id_start = 12, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 97, .range_length = 26, .glyph_id_start = 38, + .unicode_list = NULL, .glyph_id_ofs_list = NULL, .list_length = 0, .type = LV_FONT_FMT_TXT_CMAP_FORMAT0_TINY + }, + { + .range_start = 176, .range_length = 58, .glyph_id_start = 64, + .unicode_list = unicode_list_3, .glyph_id_ofs_list = NULL, .list_length = 2, .type = LV_FONT_FMT_TXT_CMAP_SPARSE_TINY + } +}; + +/*----------------- + * KERNING + *----------------*/ + + +/*Map glyph_ids to kern left classes*/ +static const uint8_t kern_left_class_mapping[] = +{ + 0, 1, 2, 0, 3, 4, 5, 6, + 7, 8, 9, 2, 10, 11, 12, 13, + 14, 15, 16, 17, 17, 18, 19, 20, + 17, 17, 13, 21, 13, 22, 23, 24, + 18, 25, 25, 26, 27, 28, 29, 30, + 31, 32, 33, 34, 35, 29, 35, 35, + 36, 32, 29, 29, 30, 30, 37, 38, + 39, 40, 35, 41, 41, 42, 41, 43, + 44, 33 +}; + +/*Map glyph_ids to kern right classes*/ +static const uint8_t kern_right_class_mapping[] = +{ + 0, 1, 2, 3, 4, 5, 6, 7, + 2, 8, 9, 10, 11, 12, 13, 12, + 12, 12, 13, 12, 12, 14, 12, 12, + 12, 12, 13, 12, 13, 12, 15, 16, + 17, 18, 18, 19, 20, 21, 22, 23, + 24, 24, 24, 0, 24, 23, 25, 26, + 23, 23, 27, 27, 24, 27, 24, 27, + 28, 29, 30, 31, 31, 32, 31, 33, + 34, 24 +}; + +/*Kern values between classes*/ +static const int8_t kern_class_values[] = +{ + 0, -3, -3, 3, 3, -2, 0, -3, + 3, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -16, -3, 0, -1, -1, -3, 0, + 0, -2, 0, 0, -2, 0, 0, -6, + 0, -5, 0, -6, -8, -8, -5, 0, + 0, 0, 0, -2, 0, 0, 3, 0, + 2, -3, 0, 1, 3, -1, 0, 0, + 0, -5, 0, -1, 0, 0, 1, 0, + 0, 3, 0, -2, 0, -3, 0, -4, + 0, 0, 0, -3, 0, 0, 0, 0, + 0, -1, 1, -2, -2, 0, 0, 0, + 0, -1, -1, 0, -3, -3, 0, 0, + 1, 0, 0, 0, 0, -2, 0, -3, + -3, -3, 0, 0, 0, 0, 0, -2, + 0, 0, 0, 0, -2, -3, 0, -4, + 5, 0, -6, -1, -3, 0, -1, -12, + 3, -2, 0, 0, 3, 1, -2, -13, + 0, -14, -2, -22, -2, 7, 0, 3, + 0, 0, 0, 0, 1, 0, -5, -3, + 0, -8, 0, 0, 0, -1, -1, 0, + -1, -3, 0, 0, 0, 0, 0, -3, + 0, -3, 0, -2, -3, -2, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + -2, -2, 0, -3, 3, 0, 0, 0, + 0, 0, 0, -2, 0, 0, 2, 0, + 0, 0, 0, -3, 0, -3, -2, -3, + 0, 0, 0, 2, 0, -2, 0, 0, + 0, 0, -3, -4, 0, -5, -13, -5, + 3, 0, -2, -17, -5, 0, -5, 0, + -16, 0, -5, -7, -2, 0, 0, 1, + -1, 2, -2, -10, 0, -13, -6, -5, + -6, -8, -3, -7, -1, -5, -7, 2, + 3, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -1, 0, 0, -1, 0, -3, + 0, -4, -6, -6, -1, 0, 0, 0, + 0, -2, 0, 0, 0, 0, 1, -2, + 0, 0, 8, -2, -11, 0, 3, -4, + 0, -13, -1, -3, 3, 0, -3, 4, + 0, -9, -4, -9, -8, -11, 0, 0, + 0, -1, 0, 0, 0, -1, -1, -3, + -7, -8, -1, -24, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -3, 0, -1, -3, -4, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 3, -6, + 3, -2, -1, -7, -3, 0, -3, -3, + -4, 0, -4, 0, -1, -2, -1, -2, + -4, -3, 0, -2, 0, -6, 0, 0, + 0, -5, 0, -4, 0, -4, -4, 3, + -5, 0, -3, -3, -3, 0, 0, 0, + 0, 0, -3, 0, 0, -4, 0, -3, + 0, -6, -6, -8, -2, 0, 0, 0, + 0, 20, 0, 0, 1, 0, 0, -3, + 0, 3, 3, -4, 0, -2, -3, -8, + -2, -2, -2, -1, 0, 0, -1, 0, + 0, 0, 0, -3, -2, -2, 0, -2, + 0, -2, 0, 0, 0, -2, -3, -2, + -2, -3, -2, 0, -3, -3, 4, 0, + 0, -12, -4, 3, -4, 2, -8, 0, + -2, -4, -1, 1, 0, 0, -4, 0, + 0, -5, 0, -4, -3, -4, -3, -3, + 0, -4, 1, -5, -4, 8, 3, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, -2, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, -4, 0, 0, 0, + 0, -3, 0, 0, -3, -3, 0, 0, + 0, 0, 0, -1, 0, 0, 0, 0, + 0, -2, 0, 0, 0, -6, 5, 1, + -2, -12, 0, 0, -6, -3, -7, 0, + -6, 0, -4, -11, -3, -10, -10, -12, + 0, -3, 0, -6, -3, -1, -3, -4, + -7, -5, -9, -10, -6, -3, 8, -6, + -9, 0, 1, -8, 0, -13, -2, -3, + 1, 0, -3, 0, -2, -17, -3, -13, + -3, -19, 0, 1, 0, -2, 0, 0, + 0, 0, -1, -2, -10, -2, 0, -17, + -7, 0, 0, -1, -4, -8, -3, 0, + -2, 0, -12, -3, 0, -8, 0, -8, + -2, -4, -6, -3, -4, -4, 0, -3, + -5, -3, -5, 0, 1, 0, -2, -8, + 0, 5, 0, 0, 0, 0, -2, -5, + 0, 0, 0, 0, 0, 0, 0, -3, + 0, -3, 0, 0, -5, -3, 0, -1, + 0, 0, 0, 0, 0, 0, 1, 0, + 0, 0, 0, 4, 5, 0, -3, 0, + -2, 3, 0, -3, 0, -3, 0, 0, + 0, 0, 0, -3, 0, 0, -3, -4, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -3, -3, 0, -4, -8, -5, + 10, 5, 3, -22, -2, 5, -3, 0, + -9, 0, -3, -3, -2, 3, -3, -2, + -8, -2, 0, -7, 0, -14, -3, 7, + -3, -10, 1, -3, -8, -8, -3, 10, + -9, -6, 8, 0, 1, -19, -2, 3, + -4, -2, -9, -4, -6, -4, -4, -2, + 0, 0, -6, -5, -3, -14, 0, -14, + -4, 0, -9, -15, -1, -8, -4, -8, + -7, 7, 0, -8, 3, 0, 0, -14, + 0, -3, -6, -4, -8, -6, -6, 0, + -3, -8, -3, -6, -5, -8, -3, -4, + 0, -8, -3, 0, -3, -5, -6, -7, + -7, -10, -3, -5, -9, -8, 8, -3, + 1, -24, -5, 5, -6, -4, -11, -3, + -8, -3, -4, -2, -3, -5, -8, -1, + 0, -17, 0, -15, -6, 6, -10, -17, + -5, -9, -11, -13, -8, 5, 5, -5, + 5, 0, 0, -8, -1, 0, -1, 0, + 0, 0, -2, 0, 0, 0, 0, 0, + -3, 0, 0, 1, 0, -3, 0, 0, + 0, 0, -2, -2, -3, 0, 0, 0, + 0, 0, -6, -1, 0, 0, 0, -6, + 0, -3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 1, + 0, 0, 0, 0, 0, 0, -3, 0, + 0, -5, -3, 0, -7, -3, -6, 0, + 0, -7, 0, -3, -3, 0, 0, 0, + 0, -21, -5, -10, -3, -9, 0, -1, + 0, 0, 0, 0, 0, 0, 0, 0, + -4, -5, -2, -4, 5, -2, -6, -2, + -4, -5, 0, -3, -1, -2, 0, 0, + -1, 0, 0, -23, -2, -4, 0, -6, + 0, 0, -2, -2, 0, 0, 0, 0, + 2, 0, -2, -4, -2, 4, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, 0, 0, + 0, 0, -7, -3, -5, 0, 0, -7, + 0, -3, 0, 0, 0, 0, 0, -25, + 0, -5, -9, -13, 0, -4, 0, 0, + 0, 0, 0, 0, 0, 0, -3, -4, + -1, -4, -3, 3, 13, 4, 6, -7, + 3, 11, 3, 7, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, -3, + 0, -2, 20, 11, 20, 0, 0, 0, + 3, 0, 0, 9, 0, 0, -2, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -4, -22, -3, -2, -10, -13, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 3, -3, + 2, 5, 3, -8, 0, -1, -2, 3, + 0, 0, 0, 0, 0, -6, 0, -2, + -2, -5, 0, -3, 0, -6, -2, 0, + -2, -4, 0, -3, -7, -5, -3, 0, + 0, 0, -2, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, -4, -22, + -3, -2, -10, -13, 0, 0, 0, 0, + 0, 13, 0, 0, 0, 0, 0, 0, + 0, 0, -3, 1, -2, 1, -2, -7, + 1, 6, 1, 2, -10, -3, -6, 0, + -4, -10, -5, -7, -11, -10, 0, -2, + -2, -3, -2, 0, -2, -1, 4, 0, + 4, -2, 0, 8, 0, 0, -2, -3, + -3, 0, 0, -7, 0, -1, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, -3, -3, 0, -3, 3, -4, + -5, -2, 0, -7, -2, -6, -2, -3, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, -5, 0, 0, + 0, 0, -3, 0, -3, 0, 0, -1, + -8, 2, 3, 3, -1, -7, 2, 4, + 2, 8, -7, 0, -2, 0, -2, -10, + 0, 0, -8, -7, 0, -4, 0, -4, + 0, -4, 0, -2, 4, 0, -2, -8, + -3, 9, 0, -3, 2, 0, 0, -8, + 0, -2, -1, 0, 0, 0, -2, 0, + -2, -10, -3, -6, 0, -8, 0, -3, + 0, -5, 0, 2, 0, -3, 0, -3, + -8, 0, -3, 3, 1, 0, -3, -2, + 0, -3, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, -2, 0, 0, 0, 0, + 1, 0, -3, -3, 0, 0, -16, 1, + 11, 8, 4, -10, 2, 11, 0, 9, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0 +}; + + +/*Collect the kern class' data in one place*/ +static const lv_font_fmt_txt_kern_classes_t kern_classes = +{ + .class_pair_values = kern_class_values, + .left_class_mapping = kern_left_class_mapping, + .right_class_mapping = kern_right_class_mapping, + .left_class_cnt = 44, + .right_class_cnt = 34, +}; + +/*-------------------- + * ALL CUSTOM DATA + *--------------------*/ + +#if LVGL_VERSION_MAJOR == 8 +/*Store all the custom data of the font*/ +static lv_font_fmt_txt_glyph_cache_t cache; +#endif + +#if LVGL_VERSION_MAJOR >= 8 +static const lv_font_fmt_txt_dsc_t font_dsc = { +#else +static lv_font_fmt_txt_dsc_t font_dsc = { +#endif + .glyph_bitmap = glyph_bitmap, + .glyph_dsc = glyph_dsc, + .cmaps = cmaps, + .kern_dsc = &kern_classes, + .kern_scale = 16, + .cmap_num = 4, + .bpp = 1, + .kern_classes = 1, + .bitmap_format = 0, +#if LVGL_VERSION_MAJOR == 8 + .cache = &cache +#endif +}; + + + +/*----------------- + * PUBLIC FONT + *----------------*/ + +/*Initialize a public general font descriptor*/ +#if LVGL_VERSION_MAJOR >= 8 +const lv_font_t notomedium16 = { +#else +lv_font_t notomedium16 = { +#endif + .get_glyph_dsc = lv_font_get_glyph_dsc_fmt_txt, /*Function pointer to get glyph's data*/ + .get_glyph_bitmap = lv_font_get_bitmap_fmt_txt, /*Function pointer to get glyph's bitmap*/ + .line_height = 15, /*The maximum line height required by the font*/ + .base_line = 3, /*Baseline measured from the bottom of the line*/ +#if !(LVGL_VERSION_MAJOR == 6 && LVGL_VERSION_MINOR == 0) + .subpx = LV_FONT_SUBPX_NONE, +#endif +#if LV_VERSION_CHECK(7, 4, 0) || LVGL_VERSION_MAJOR >= 8 + .underline_position = -1, + .underline_thickness = 1, +#endif + .dsc = &font_dsc, /*The custom font data. Will be accessed by `get_glyph_bitmap/dsc` */ +#if LV_VERSION_CHECK(8, 2, 0) || LVGL_VERSION_MAJOR >= 9 + .fallback = NULL, +#endif + .user_data = NULL, +}; + + + +#endif /*#if NOTOMEDIUM16*/ + diff --git a/main/idf_component.yml b/main/idf_component.yml index 8343ec4..a26fb54 100644 --- a/main/idf_component.yml +++ b/main/idf_component.yml @@ -1,4 +1,6 @@ dependencies: + suda-morris/am2302_rmt: "^1.0.0" + espressif/esp_websocket_client: "^1.3.0" joltwallet/littlefs: ^1.14.8 esp_lcd_touch_gt911: version: ^1 diff --git a/main/images/E.svg b/main/images/E.svg deleted file mode 100644 index 3b22d27..0000000 --- a/main/images/E.svg +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - diff --git a/main/images/ENE.svg b/main/images/ENE.svg deleted file mode 100644 index 98c9ea5..0000000 --- a/main/images/ENE.svg +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - diff --git a/main/images/ESE.svg b/main/images/ESE.svg deleted file mode 100644 index ea46c7a..0000000 --- a/main/images/ESE.svg +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - diff --git a/main/images/N.svg b/main/images/N.svg deleted file mode 100644 index 2c9c9b0..0000000 --- a/main/images/N.svg +++ /dev/null @@ -1,10 +0,0 @@ - - - - - - - diff --git a/main/images/NNO.svg b/main/images/NNO.svg deleted file mode 100644 index da95d7d..0000000 --- a/main/images/NNO.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/NO.svg b/main/images/NO.svg deleted file mode 100644 index 9c69f46..0000000 --- a/main/images/NO.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/O.svg b/main/images/O.svg deleted file mode 100644 index 74ba9c7..0000000 --- a/main/images/O.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/ONO.svg b/main/images/ONO.svg deleted file mode 100644 index b1142fa..0000000 --- a/main/images/ONO.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/OSO.svg b/main/images/OSO.svg deleted file mode 100644 index 1e5f4c1..0000000 --- a/main/images/OSO.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/S.svg b/main/images/S.svg deleted file mode 100644 index 3e31dd5..0000000 --- a/main/images/S.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/SE.svg b/main/images/SE.svg deleted file mode 100644 index 7d20d7c..0000000 --- a/main/images/SE.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/SO.svg b/main/images/SO.svg deleted file mode 100644 index d4d955e..0000000 --- a/main/images/SO.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/SSE.svg b/main/images/SSE.svg deleted file mode 100644 index 9b5c96f..0000000 --- a/main/images/SSE.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/SSO.svg b/main/images/SSO.svg deleted file mode 100644 index 0dad2e5..0000000 --- a/main/images/SSO.svg +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - diff --git a/main/images/Variable.svg b/main/images/Variable.svg index d541ce2..f7a7a78 100644 --- a/main/images/Variable.svg +++ b/main/images/Variable.svg @@ -1,10 +1,10 @@ - - - - - - + + + + + + diff --git a/main/images/images.txt b/main/images/images.txt deleted file mode 100644 index ad6eac8..0000000 --- a/main/images/images.txt +++ /dev/null @@ -1,27 +0,0 @@ -E -ENE -ESE -N -NNO -NO -O -ONO -OSO -S -SE -SO -SSE -SSO -Variable -p14bisj -p14j -p16bisj -p1j -p1n -p26j -p26n -p29j -p2j -p2n -p4j -p4n diff --git a/main/images/p10j.svg b/main/images/p10j.svg deleted file mode 100644 index 18ac3dd..0000000 --- a/main/images/p10j.svg +++ /dev/null @@ -1 +0,0 @@ -14Plan de travail 1 \ No newline at end of file diff --git a/main/images/p10n.svg b/main/images/p10n.svg deleted file mode 100644 index 755ba89..0000000 --- a/main/images/p10n.svg +++ /dev/null @@ -1 +0,0 @@ -15Plan de travail 1 \ No newline at end of file diff --git a/main/images/p11j.svg b/main/images/p11j.svg deleted file mode 100644 index 8aafd2a..0000000 --- a/main/images/p11j.svg +++ /dev/null @@ -1,46 +0,0 @@ - - - - -16Plan de travail 1 - - - - - - - - - - - - - - - - - - diff --git a/main/images/p11n.svg b/main/images/p11n.svg deleted file mode 100644 index d436eb0..0000000 --- a/main/images/p11n.svg +++ /dev/null @@ -1,46 +0,0 @@ - - - - -16Plan de travail 1 - - - - - - - - - - - - - - - - - - diff --git a/main/images/p12bisj.svg b/main/images/p12bisj.svg deleted file mode 100644 index 79d49c1..0000000 --- a/main/images/p12bisj.svg +++ /dev/null @@ -1,49 +0,0 @@ - - - - -17Plan de travail 1 - - - - - - - - - - - - - - - - - - diff --git a/main/images/p12j.svg b/main/images/p12j.svg deleted file mode 100644 index 89eab7f..0000000 --- a/main/images/p12j.svg +++ /dev/null @@ -1 +0,0 @@ -17Plan de travail 1 \ No newline at end of file diff --git a/main/images/p12n.svg b/main/images/p12n.svg deleted file mode 100644 index 251e569..0000000 --- a/main/images/p12n.svg +++ /dev/null @@ -1 +0,0 @@ -18Plan de travail 1 \ No newline at end of file diff --git a/main/images/p13j.svg b/main/images/p13j.svg deleted file mode 100644 index eeab9da..0000000 --- a/main/images/p13j.svg +++ /dev/null @@ -1,45 +0,0 @@ - - - - -19Plan de travail 1 - - - - - - - - - - - - - - - - diff --git a/main/images/p13n.svg b/main/images/p13n.svg deleted file mode 100644 index 1e0ab84..0000000 --- a/main/images/p13n.svg +++ /dev/null @@ -1,45 +0,0 @@ - - - - -19Plan de travail 1 - - - - - - - - - - - - - - - - diff --git a/main/images/p14bisj.svg b/main/images/p14bisj.svg deleted file mode 100644 index f4d39fc..0000000 --- a/main/images/p14bisj.svg +++ /dev/null @@ -1,55 +0,0 @@ - - - - -22Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p14j.svg b/main/images/p14j.svg deleted file mode 100644 index 69f63ea..0000000 --- a/main/images/p14j.svg +++ /dev/null @@ -1,55 +0,0 @@ - - - - -22Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p14n.svg b/main/images/p14n.svg deleted file mode 100644 index ec8394d..0000000 --- a/main/images/p14n.svg +++ /dev/null @@ -1,55 +0,0 @@ - - - - -22Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p15j.svg b/main/images/p15j.svg deleted file mode 100644 index 5e93c4c..0000000 --- a/main/images/p15j.svg +++ /dev/null @@ -1,33 +0,0 @@ - - - - -23Plan de travail 1 - - - - - - - - - - - diff --git a/main/images/p15n.svg b/main/images/p15n.svg deleted file mode 100644 index 578494c..0000000 --- a/main/images/p15n.svg +++ /dev/null @@ -1,33 +0,0 @@ - - - - -23Plan de travail 1 - - - - - - - - - - - diff --git a/main/images/p16bisj.svg b/main/images/p16bisj.svg deleted file mode 100644 index 1192aa5..0000000 --- a/main/images/p16bisj.svg +++ /dev/null @@ -1,47 +0,0 @@ - - - - -26Plan de travail 1 - - - - - - - - - - - - - - - - - diff --git a/main/images/p16j.svg b/main/images/p16j.svg deleted file mode 100644 index 5ce591b..0000000 --- a/main/images/p16j.svg +++ /dev/null @@ -1,47 +0,0 @@ - - - - -26Plan de travail 1 - - - - - - - - - - - - - - - - - diff --git a/main/images/p16n.svg b/main/images/p16n.svg deleted file mode 100644 index 8774a4b..0000000 --- a/main/images/p16n.svg +++ /dev/null @@ -1,47 +0,0 @@ - - - - -26Plan de travail 1 - - - - - - - - - - - - - - - - - diff --git a/main/images/p17j.svg b/main/images/p17j.svg deleted file mode 100644 index 8228888..0000000 --- a/main/images/p17j.svg +++ /dev/null @@ -1 +0,0 @@ -27Plan de travail 1 \ No newline at end of file diff --git a/main/images/p17n.svg b/main/images/p17n.svg deleted file mode 100644 index 1f280ff..0000000 --- a/main/images/p17n.svg +++ /dev/null @@ -1 +0,0 @@ -28Plan de travail 1 \ No newline at end of file diff --git a/main/images/p18j.svg b/main/images/p18j.svg deleted file mode 100644 index 330632c..0000000 --- a/main/images/p18j.svg +++ /dev/null @@ -1,33 +0,0 @@ - - - - -29Plan de travail 1 - - - - - - - - - diff --git a/main/images/p18n.svg b/main/images/p18n.svg deleted file mode 100644 index 4f17381..0000000 --- a/main/images/p18n.svg +++ /dev/null @@ -1,33 +0,0 @@ - - - - -29Plan de travail 1 - - - - - - - - - diff --git a/main/images/p19j.svg b/main/images/p19j.svg deleted file mode 100644 index 5e949b7..0000000 --- a/main/images/p19j.svg +++ /dev/null @@ -1 +0,0 @@ -30Plan de travail 1 \ No newline at end of file diff --git a/main/images/p19n.svg b/main/images/p19n.svg deleted file mode 100644 index c4868fe..0000000 --- a/main/images/p19n.svg +++ /dev/null @@ -1 +0,0 @@ -31Plan de travail 1 \ No newline at end of file diff --git a/main/images/p1j.svg b/main/images/p1j.svg deleted file mode 100644 index 5e6a895..0000000 --- a/main/images/p1j.svg +++ /dev/null @@ -1 +0,0 @@ -Plan de travail 1 \ No newline at end of file diff --git a/main/images/p1n.svg b/main/images/p1n.svg deleted file mode 100644 index f5a7231..0000000 --- a/main/images/p1n.svg +++ /dev/null @@ -1 +0,0 @@ -2Plan de travail 1 \ No newline at end of file diff --git a/main/images/p20j.svg b/main/images/p20j.svg deleted file mode 100644 index 02b2327..0000000 --- a/main/images/p20j.svg +++ /dev/null @@ -1,58 +0,0 @@ - - - - -32Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p20n.svg b/main/images/p20n.svg deleted file mode 100644 index f1275b6..0000000 --- a/main/images/p20n.svg +++ /dev/null @@ -1,58 +0,0 @@ - - - - -32Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p21j.svg b/main/images/p21j.svg deleted file mode 100644 index 78e2542..0000000 --- a/main/images/p21j.svg +++ /dev/null @@ -1 +0,0 @@ -33Plan de travail 1 \ No newline at end of file diff --git a/main/images/p21n.svg b/main/images/p21n.svg deleted file mode 100644 index 25f645a..0000000 --- a/main/images/p21n.svg +++ /dev/null @@ -1 +0,0 @@ -34Plan de travail 1 \ No newline at end of file diff --git a/main/images/p22j.svg b/main/images/p22j.svg deleted file mode 100644 index d3081d2..0000000 --- a/main/images/p22j.svg +++ /dev/null @@ -1 +0,0 @@ -35Plan de travail 1 \ No newline at end of file diff --git a/main/images/p22n.svg b/main/images/p22n.svg deleted file mode 100644 index d3081d2..0000000 --- a/main/images/p22n.svg +++ /dev/null @@ -1 +0,0 @@ -35Plan de travail 1 \ No newline at end of file diff --git a/main/images/p23j.svg b/main/images/p23j.svg deleted file mode 100644 index 4147a79..0000000 --- a/main/images/p23j.svg +++ /dev/null @@ -1 +0,0 @@ -36Plan de travail 1 \ No newline at end of file diff --git a/main/images/p23n.svg b/main/images/p23n.svg deleted file mode 100644 index 4147a79..0000000 --- a/main/images/p23n.svg +++ /dev/null @@ -1 +0,0 @@ -36Plan de travail 1 \ No newline at end of file diff --git a/main/images/p24j.svg b/main/images/p24j.svg deleted file mode 100644 index 23cc783..0000000 --- a/main/images/p24j.svg +++ /dev/null @@ -1 +0,0 @@ -37Plan de travail 1 \ No newline at end of file diff --git a/main/images/p24n.svg b/main/images/p24n.svg deleted file mode 100644 index 9f33dc4..0000000 --- a/main/images/p24n.svg +++ /dev/null @@ -1 +0,0 @@ -38Plan de travail 1 \ No newline at end of file diff --git a/main/images/p25j.svg b/main/images/p25j.svg deleted file mode 100644 index 3c749a7..0000000 --- a/main/images/p25j.svg +++ /dev/null @@ -1 +0,0 @@ -39Plan de travail 1 \ No newline at end of file diff --git a/main/images/p25n.svg b/main/images/p25n.svg deleted file mode 100644 index 3c749a7..0000000 --- a/main/images/p25n.svg +++ /dev/null @@ -1 +0,0 @@ -39Plan de travail 1 \ No newline at end of file diff --git a/main/images/p26j.svg b/main/images/p26j.svg deleted file mode 100644 index 8190304..0000000 --- a/main/images/p26j.svg +++ /dev/null @@ -1 +0,0 @@ -40Plan de travail 1 \ No newline at end of file diff --git a/main/images/p26n.svg b/main/images/p26n.svg deleted file mode 100644 index 8506f0a..0000000 --- a/main/images/p26n.svg +++ /dev/null @@ -1 +0,0 @@ -41Plan de travail 1 \ No newline at end of file diff --git a/main/images/p27j.svg b/main/images/p27j.svg deleted file mode 100644 index 75ba956..0000000 --- a/main/images/p27j.svg +++ /dev/null @@ -1 +0,0 @@ -42Plan de travail 1 \ No newline at end of file diff --git a/main/images/p27n.svg b/main/images/p27n.svg deleted file mode 100644 index 75ba956..0000000 --- a/main/images/p27n.svg +++ /dev/null @@ -1 +0,0 @@ -42Plan de travail 1 \ No newline at end of file diff --git a/main/images/p28j.svg b/main/images/p28j.svg deleted file mode 100644 index c13afb9..0000000 --- a/main/images/p28j.svg +++ /dev/null @@ -1 +0,0 @@ -43Plan de travail 1 \ No newline at end of file diff --git a/main/images/p28n.svg b/main/images/p28n.svg deleted file mode 100644 index 9c117fc..0000000 --- a/main/images/p28n.svg +++ /dev/null @@ -1 +0,0 @@ -44Plan de travail 1 \ No newline at end of file diff --git a/main/images/p29j.svg b/main/images/p29j.svg deleted file mode 100644 index 40dc7ff..0000000 --- a/main/images/p29j.svg +++ /dev/null @@ -1 +0,0 @@ -45Plan de travail 1 \ No newline at end of file diff --git a/main/images/p29n.svg b/main/images/p29n.svg deleted file mode 100644 index 40dc7ff..0000000 --- a/main/images/p29n.svg +++ /dev/null @@ -1 +0,0 @@ -45Plan de travail 1 \ No newline at end of file diff --git a/main/images/p30j.svg b/main/images/p30j.svg deleted file mode 100644 index 5417c00..0000000 --- a/main/images/p30j.svg +++ /dev/null @@ -1,35 +0,0 @@ - - - - - - - - - - - - - - - diff --git a/main/images/p30n.svg b/main/images/p30n.svg deleted file mode 100644 index 85f1a1c..0000000 --- a/main/images/p30n.svg +++ /dev/null @@ -1,52 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p31j.svg b/main/images/p31j.svg deleted file mode 100644 index 7e4d761..0000000 --- a/main/images/p31j.svg +++ /dev/null @@ -1,73 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p31n.svg b/main/images/p31n.svg deleted file mode 100644 index a41814b..0000000 --- a/main/images/p31n.svg +++ /dev/null @@ -1,73 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p32j.svg b/main/images/p32j.svg deleted file mode 100644 index 28ba3a1..0000000 --- a/main/images/p32j.svg +++ /dev/null @@ -1,63 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p32n.svg b/main/images/p32n.svg deleted file mode 100644 index 61adce4..0000000 --- a/main/images/p32n.svg +++ /dev/null @@ -1,63 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p3j.svg b/main/images/p3j.svg deleted file mode 100644 index b1037b2..0000000 --- a/main/images/p3j.svg +++ /dev/null @@ -1 +0,0 @@ -7Plan de travail 1 \ No newline at end of file diff --git a/main/images/p3n.svg b/main/images/p3n.svg deleted file mode 100644 index 4b8548f..0000000 --- a/main/images/p3n.svg +++ /dev/null @@ -1 +0,0 @@ -7Plan de travail 1 \ No newline at end of file diff --git a/main/images/p4j.svg b/main/images/p4j.svg deleted file mode 100644 index d3ee72a..0000000 --- a/main/images/p4j.svg +++ /dev/null @@ -1,17 +0,0 @@ - - - - - - - - - diff --git a/main/images/p4n.svg b/main/images/p4n.svg deleted file mode 100644 index 1d76805..0000000 --- a/main/images/p4n.svg +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - diff --git a/main/images/p5bisj.svg b/main/images/p5bisj.svg deleted file mode 100644 index c8e71fa..0000000 --- a/main/images/p5bisj.svg +++ /dev/null @@ -1,26 +0,0 @@ - - - - -8Plan de travail 1 - - - - - - - - - diff --git a/main/images/p5bisj.svg.1 b/main/images/p5bisj.svg.1 deleted file mode 100644 index c8e71fa..0000000 --- a/main/images/p5bisj.svg.1 +++ /dev/null @@ -1,26 +0,0 @@ - - - - -8Plan de travail 1 - - - - - - - - - diff --git a/main/images/p5j.svg b/main/images/p5j.svg deleted file mode 100644 index fe65180..0000000 --- a/main/images/p5j.svg +++ /dev/null @@ -1 +0,0 @@ -8Plan de travail 1 \ No newline at end of file diff --git a/main/images/p5n.svg b/main/images/p5n.svg deleted file mode 100644 index bc31ca3..0000000 --- a/main/images/p5n.svg +++ /dev/null @@ -1 +0,0 @@ -9Plan de travail 1 \ No newline at end of file diff --git a/main/images/p6j.svg b/main/images/p6j.svg deleted file mode 100644 index 4e18b10..0000000 --- a/main/images/p6j.svg +++ /dev/null @@ -1,22 +0,0 @@ - - - - -10Plan de travail 1 - - - - - - - diff --git a/main/images/p6n.svg b/main/images/p6n.svg deleted file mode 100644 index e30e77a..0000000 --- a/main/images/p6n.svg +++ /dev/null @@ -1,22 +0,0 @@ - - - - -10Plan de travail 1 - - - - - - - diff --git a/main/images/p7j.svg b/main/images/p7j.svg deleted file mode 100644 index 6aa374d..0000000 --- a/main/images/p7j.svg +++ /dev/null @@ -1,34 +0,0 @@ - - - - -11Plan de travail 1 - - - - - - - - - - - - - diff --git a/main/images/p7n.svg b/main/images/p7n.svg deleted file mode 100644 index c1c86d8..0000000 --- a/main/images/p7n.svg +++ /dev/null @@ -1,34 +0,0 @@ - - - - -11Plan de travail 1 - - - - - - - - - - - - - diff --git a/main/images/p8j.svg b/main/images/p8j.svg deleted file mode 100644 index e80f3db..0000000 --- a/main/images/p8j.svg +++ /dev/null @@ -1,45 +0,0 @@ - - - - -12Plan de travail 1 - - - - - - - - - - - - - - - - - - diff --git a/main/images/p8n.svg b/main/images/p8n.svg deleted file mode 100644 index 9b0c280..0000000 --- a/main/images/p8n.svg +++ /dev/null @@ -1,45 +0,0 @@ - - - - -12Plan de travail 1 - - - - - - - - - - - - - - - - - - diff --git a/main/images/p9j.svg b/main/images/p9j.svg deleted file mode 100644 index f6cdfdf..0000000 --- a/main/images/p9j.svg +++ /dev/null @@ -1,51 +0,0 @@ - - - - -13Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/p9n.svg b/main/images/p9n.svg deleted file mode 100644 index 8a6782d..0000000 --- a/main/images/p9n.svg +++ /dev/null @@ -1,51 +0,0 @@ - - - - -13Plan de travail 1 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/main/images/plan_etage.c:Zone.Identifier b/main/images/plan_etage.c:Zone.Identifier new file mode 100644 index 0000000..053d112 --- /dev/null +++ b/main/images/plan_etage.c:Zone.Identifier @@ -0,0 +1,3 @@ +[ZoneTransfer] +ZoneId=3 +HostUrl=about:internet diff --git a/main/images/plan_rdc.c:Zone.Identifier b/main/images/plan_rdc.c:Zone.Identifier new file mode 100644 index 0000000..053d112 --- /dev/null +++ b/main/images/plan_rdc.c:Zone.Identifier @@ -0,0 +1,3 @@ +[ZoneTransfer] +ZoneId=3 +HostUrl=about:internet diff --git a/main/images/wifi_ko_orig.png:Zone.Identifier b/main/images/wifi_ko_orig.png:Zone.Identifier new file mode 100644 index 0000000..8437b5e --- /dev/null +++ b/main/images/wifi_ko_orig.png:Zone.Identifier @@ -0,0 +1,4 @@ +[ZoneTransfer] +ZoneId=3 +ReferrerUrl=https://www.flaticon.com/free-icon/wifi_10179082?term=wifi&page=1&position=72&origin=tag&related_id=10179082 +HostUrl=https://www.flaticon.com/download/icon/10179082?icon_id=10179082&author=4014&team=4014&keyword=Wifi&pack=10178962&style=black+outline&style_id=1369&format=png&color=%23000000&colored=1&size=512&selection=1&type=standard&token=03AFcWeA4RyxIf4QsrIC4tHTqrKilxyFhDaeCELUJ5y2sh5Z335A3k8sZtFRKbUkQjtMRnLVYnKYcv-jzbF73QhCKZMOKukL3s8JLvWQvNyitg0AK2yFN9cm6zn8bhADDZASUE7dAtq2wzDW9Q4xndpF9QSqs7esAvmn7a7sFjD5RF2nbQLj8tSNkchXBvh9Tqfr_3-4FOMk7yNRwUNWUGRHYa_7HL8k24iA_UjL7hDHY21uNBBwEbwmsOtQSMiFog7JBJ7c6QimbJuJFvUq2OaDOvp3XRh0QwfgMzIZR-0eSwHUTNZK0ZvfR-78QJFjvMEOjIZWwvLabNeJk1twjloLXxYWT-VKxk1jRjHxAGVUGH3wm7YSMlgMScDjLDH0ysTezlCo3YIyuFdPSNadc5Y8bLmhc84f0f0YnKzjVLS4YwUO5rLMrG5jx7hvUEuWzny7mWE9N2QstAIC7OTEWRUU9tA2TS_NPlg8yl5YU5KTcgUIojGXyOe4grWD-4TYgKW_Uzu6sQ2iHZWPYWQf3rNjX4GWTHcpDgD3ccNgzb8HeXhQdYE1Rf9W9WAA_amhHnPYZmatQSy9mHCnb80FjnYcbKUwcRMD2hQbPGzF78YqKH5smnThi8V_gsXZvfG8pb6RKfSzf-CK05fKRcvCgr6D-P7dN67GtxrvCt_If3c_X329lw8FYZuGJFHBb5aDgpcVieIOECR6afx2JMb-aesRBEZDNSXuQ7haFyHe_XcD4jqksyCslN3akqmyAx72i3Lg1t7tqEQCFGY_4WsWjHYB2LgwZIss2anRN7Gddg7p4G4fC1sKfSGRCZMIHfutZv0phQNI6OoYGnC8I3dxkW__w1trG7NCWw04Zb4sUpHnqEFpO2ujdoApltxHdcaCPkjT_ojghjjwws_MZZBbBaetGp7B3mYNYiTX0MDtNaYfU6GnP4v3t9mnEKZxfkhMadPW2lcdSc5wDLSXjftxrPOwUUSpS39QHQ7Y-o4L3X0-cedUnrAdjEPH-3i6UfAuDtinqKomkoxlUnGjHvwyDQn-27tWB_EM7X8qdkMu2B3iYpUGTSI6Fr62m2CQjwEI5TPs_556kkMgqKttVmt4pPiI_Imt8w9uPINaqUdR-0AunFKB87KeRLvJK1i6JIPzEAc-SnABc8ohW4m6ngwC3I3dr80nLIwsZo8x9v_p3y2A8DkQPlXPHsUEpBqbM6ZM-Mq1ZK_E0IB-cdbwGTy6zV8JSSOANd6aj3pi7Lmt_sF1VhGPTivI7LJBT5nVW5ypnyz157iL5xbIOa9M6MbB1KtqNPRBcg1W3blhQ3DrczffVuZSoJlcPWXD6lZRAsgPkUR3PHzR2O7QdT4HM8XShoPoIswr6p74yWrO9nTasKVVCu_zL_ea1lR4NwYX10-5hB_hLewEI-Dg03R__kIeU0MNkyWkjajD7Vzn1EBWAJvbeNW73TapaiFWepy7874EQpwZw7_bNK6Qb4L7niaYyG8aGahsgtWl4CuxCJWVqo31MnAUM-j2lXSDk6zZRhZL9N7zGW_vVD7nGOVWFGIh40s-2KytHFI7WImqmiCmTEZZ9wXeRf_6qb_7OcJ8UOePwcaqL6XaNDpCeIzkF5ImSyuLbWLM9GWQGP97kpUXgO_q3FMvYaVJcOcGpZpRU3VFFbvqFVC2LEWcUqaD7SuEZvZS-VGjfVh8cNWocZ3IC_QqNu6-zGjDgpuIIuJBOh_tKy-iERl11U_GOl4ThytbKk4jOJtYFNDkNuN9TIJZqlVCYoNd6VPrnS46GrvrM7wj-LZffmuR9rVQpuxt_zrNyavPzuHbPCEkXDbhZL9ecqJkWy3b5E5V-dQoDSvDbHVxsbMZHwWflmbffCH6uf7fJvlGUNnu3LmOVUq-WuDK5invepzjtGDqOjxTeXmcGqnzvPDuoeQ8SkM04-zzk8HALtK0dRU1_Yk8gFOJOYz2ZPqWoDWoDYZml4QOo&search=wifi diff --git a/main/images/wifi_ok_orig.png:Zone.Identifier b/main/images/wifi_ok_orig.png:Zone.Identifier new file mode 100644 index 0000000..30c4775 --- /dev/null +++ b/main/images/wifi_ok_orig.png:Zone.Identifier @@ -0,0 +1,4 @@ +[ZoneTransfer] +ZoneId=3 +ReferrerUrl=https://www.flaticon.com/packs/system-and-calendar +HostUrl=https://www.flaticon.com/download/icon/10179079?icon_id=10179079&author=4014&team=4014&keyword=Wifi&pack=packs%2Fsystem-and-calendar&style=1369&format=png&color=%23000000&colored=1&size=512&selection=1&premium=0&type=standard diff --git a/main/images_meteo/p6bisj.png b/main/images_meteo/p6bisj.png new file mode 100644 index 0000000..246da99 Binary files /dev/null and b/main/images_meteo/p6bisj.png differ diff --git a/main/images_meteo/p6bisj.png:Zone.Identifier b/main/images_meteo/p6bisj.png:Zone.Identifier new file mode 100644 index 0000000..e69de29 diff --git a/main/include/fmeteod.h b/main/include/fmeteod.h index acc7586..0138963 100644 --- a/main/include/fmeteod.h +++ b/main/include/fmeteod.h @@ -1,83 +1,83 @@ -static void weatherdata_obs_cb(lv_observer_t *observer, lv_subject_t *subject) -{ - // Retrieve weatherdata - struct meteodailyforecast_data *data = subject->value.pointer; - //printffd(data); - char buff[40] = {}; - // sprintf(buff,"%s %.1f %.1f", data->previsions.desc, data->previsions.min, data->previsions.max); - - lv_obj_t *parent = (lv_obj_t *)(observer->target); - lv_obj_t *datefld = lv_obj_get_child(parent, 0); - lv_obj_t *desc_icon = lv_obj_get_child(parent, 1); - lv_obj_t *temps = lv_obj_get_child(parent, 2); - if (strcmp(data->previsions.icon, "p1j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p1j); - }else if (strcmp(data->previsions.icon, "p2j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p2j); - }else if (strcmp(data->previsions.icon, "p3j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p3j); - }else if (strcmp(data->previsions.icon, "p5bisj") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p5bisj); - }else if (strcmp(data->previsions.icon, "p12j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p12j); - }else if (strcmp(data->previsions.icon, "p12bisj") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p12bisj); - }else if (strcmp(data->previsions.icon, "p14j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p14j); - }else if (strcmp(data->previsions.icon, "p24j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p24j); - }else if (strcmp(data->previsions.icon, "p25j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p25j); - }else if (strcmp(data->previsions.icon, "p26j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p26j); - }else if (strcmp(data->previsions.icon, "p27j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p27j); - }else if (strcmp(data->previsions.icon, "p28j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p28j); - }else if (strcmp(data->previsions.icon, "p29j") == 0) - { - lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p29j); - }else{ - ESP_LOGE(TAG, "Image %s non connue",data->previsions.icon); - } - - char buffer[80]; - dtToString(data->datetime,buffer); - - lv_label_set_text(datefld, buffer); - lv_label_set_text(lv_obj_get_child(desc_icon, 1), data->previsions.desc); - lv_label_set_text_fmt(lv_obj_get_child(temps, 0), "%.1f°C", data->previsions.max); - lv_label_set_text_fmt(lv_obj_get_child(temps, 1), "%.1f°C", data->previsions.min); -} - -struct weatherDay_fragment_t -{ - /* IMPORTANT: don't miss this part */ - lv_fragment_t base; - /* States, object references and data fields for this fragment */ - int dayNr; - bool showTitle; - const char *title; - float minTemp; - float maxTemp; -}; -static void weatherDay_fragment_ctor(lv_fragment_t *self, void * args) -{ - int dayNo = ((int *)args)[0]; - bool showDate = ((int*)args)[1]; - ((struct weatherDay_fragment_t *)self)->dayNr = dayNo; - ((struct weatherDay_fragment_t *)self)->showTitle = showDate; - ESP_LOGI(TAG, "Fragment initialisé avec le jour n°%d - Afficher la date %d",dayNo, showDate); -} +static void weatherdata_obs_cb(lv_observer_t *observer, lv_subject_t *subject) +{ + // Retrieve weatherdata + struct meteodailyforecast_data *data = subject->value.pointer; + //printffd(data); + char buff[40] = {}; + // sprintf(buff,"%s %.1f %.1f", data->previsions.desc, data->previsions.min, data->previsions.max); + + lv_obj_t *parent = (lv_obj_t *)(observer->target); + lv_obj_t *datefld = lv_obj_get_child(parent, 0); + lv_obj_t *desc_icon = lv_obj_get_child(parent, 1); + lv_obj_t *temps = lv_obj_get_child(parent, 2); + if (strcmp(data->previsions.icon, "p1j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p1j); + }else if (strcmp(data->previsions.icon, "p2j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p2j); + }else if (strcmp(data->previsions.icon, "p3j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p3j); + }else if (strcmp(data->previsions.icon, "p5bisj") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p5bisj); + }else if (strcmp(data->previsions.icon, "p12j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p12j); + }else if (strcmp(data->previsions.icon, "p12bisj") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p12bisj); + }else if (strcmp(data->previsions.icon, "p14j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p14j); + }else if (strcmp(data->previsions.icon, "p24j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p24j); + }else if (strcmp(data->previsions.icon, "p25j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p25j); + }else if (strcmp(data->previsions.icon, "p26j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p26j); + }else if (strcmp(data->previsions.icon, "p27j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p27j); + }else if (strcmp(data->previsions.icon, "p28j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p28j); + }else if (strcmp(data->previsions.icon, "p29j") == 0) + { + lv_image_set_src(lv_obj_get_child(desc_icon, 0), &p29j); + }else{ + ESP_LOGE(TAG, "Image %s non connue",data->previsions.icon); + } + + char buffer[80]; + dtToString(data->datetime,buffer); + + lv_label_set_text(datefld, buffer); + lv_label_set_text(lv_obj_get_child(desc_icon, 1), data->previsions.desc); + lv_label_set_text_fmt(lv_obj_get_child(temps, 0), "%.1f°C", data->previsions.max); + lv_label_set_text_fmt(lv_obj_get_child(temps, 1), "%.1f°C", data->previsions.min); +} + +struct weatherDay_fragment_t +{ + /* IMPORTANT: don't miss this part */ + lv_fragment_t base; + /* States, object references and data fields for this fragment */ + int dayNr; + bool showTitle; + const char *title; + float minTemp; + float maxTemp; +}; +static void weatherDay_fragment_ctor(lv_fragment_t *self, void * args) +{ + int dayNo = ((int *)args)[0]; + bool showDate = ((int*)args)[1]; + ((struct weatherDay_fragment_t *)self)->dayNr = dayNo; + ((struct weatherDay_fragment_t *)self)->showTitle = showDate; + ESP_LOGI(TAG, "Fragment initialisé avec le jour n°%d - Afficher la date %d",dayNo, showDate); +} diff --git a/main/main.c b/main/main.c index e2b428f..5935d90 100644 --- a/main/main.c +++ b/main/main.c @@ -1,1498 +1,1794 @@ -#include "misc/lv_types.h" -#include "freertos/FreeRTOS.h" -#include "freertos/event_groups.h" -#include "esp_err.h" -#include "esp_log.h" -#include "esp_check.h" -#include "driver/i2c.h" -#include "esp_lcd_panel_io.h" -#include "esp_lcd_panel_ops.h" -#include "esp_lcd_panel_rgb.h" -#include "esp_lcd_touch_gt911.h" -#include "esp_lvgl_port.h" -#include "esp_event.h" -#include "nvs_flash.h" -#include -#include "esp_vfs_fat.h" -#include "sdmmc_cmd.h" -#include - -// Includes personnels -#include "obtain_time.h" -#include "fatfs.h" -#include "meteofrance.h" -#include "image_downloader.h" -#include "wifi.h" -#include "mqtt.h" - -#include "esp_littlefs.h" - -#define MOUNT_POINT "/sdcard" -// Pin assignments can be set in menuconfig, see "SD SPI Example Configuration" menu. -// You can also change the pin assignments here by changing the following 4 lines. -#define PIN_NUM_MISO 13 -#define PIN_NUM_MOSI 11 -#define PIN_NUM_CLK 12 -#define PIN_NUM_CS 10 - - -#include "main.h" -LV_FONT_DECLARE(montserrat_medium_12) -LV_FONT_DECLARE(montserrat_medium_18) -LV_FONT_DECLARE(montserrat_medium_24) - -char *days[7]={"Dimanche","Lundi","Mardi","Mercredi","Jeudi","Vendredi","Samedi"}; -char *months[12]={"Janvier","Février","Mars","Avril","Mai","Juin","Juillet","Août","Septembre","Octobre","Novembre","Décembre"}; - -/* LCD size */ -#define EXAMPLE_LCD_H_RES (800) -#define EXAMPLE_LCD_V_RES (480) - -/* LCD settings */ -#define EXAMPLE_LCD_LVGL_FULL_REFRESH (0) -#define EXAMPLE_LCD_LVGL_DIRECT_MODE (1) -#define EXAMPLE_LCD_LVGL_AVOID_TEAR (1) -#define EXAMPLE_LCD_RGB_BOUNCE_BUFFER_MODE (1) -#define EXAMPLE_LCD_DRAW_BUFF_DOUBLE (1) -#define EXAMPLE_LCD_DRAW_BUFF_HEIGHT (100) -#define EXAMPLE_LCD_RGB_BUFFER_NUMS (2) -#define EXAMPLE_LCD_RGB_BOUNCE_BUFFER_HEIGHT (10) - -/* LCD pins */ -#define EXAMPLE_LCD_GPIO_VSYNC (GPIO_NUM_41) -#define EXAMPLE_LCD_GPIO_HSYNC (GPIO_NUM_39) -#define EXAMPLE_LCD_GPIO_DE (GPIO_NUM_40) -#define EXAMPLE_LCD_GPIO_PCLK (GPIO_NUM_42) -#define EXAMPLE_LCD_GPIO_DISP (GPIO_NUM_NC) -#define EXAMPLE_LCD_GPIO_DATA0 (GPIO_NUM_8) -#define EXAMPLE_LCD_GPIO_DATA1 (GPIO_NUM_3) -#define EXAMPLE_LCD_GPIO_DATA2 (GPIO_NUM_46) -#define EXAMPLE_LCD_GPIO_DATA3 (GPIO_NUM_9) -#define EXAMPLE_LCD_GPIO_DATA4 (GPIO_NUM_1) -#define EXAMPLE_LCD_GPIO_DATA5 (GPIO_NUM_5) -#define EXAMPLE_LCD_GPIO_DATA6 (GPIO_NUM_6) -#define EXAMPLE_LCD_GPIO_DATA7 (GPIO_NUM_7) -#define EXAMPLE_LCD_GPIO_DATA8 (GPIO_NUM_15) -#define EXAMPLE_LCD_GPIO_DATA9 (GPIO_NUM_16) -#define EXAMPLE_LCD_GPIO_DATA10 (GPIO_NUM_4) -#define EXAMPLE_LCD_GPIO_DATA11 (GPIO_NUM_45) -#define EXAMPLE_LCD_GPIO_DATA12 (GPIO_NUM_48) -#define EXAMPLE_LCD_GPIO_DATA13 (GPIO_NUM_47) -#define EXAMPLE_LCD_GPIO_DATA14 (GPIO_NUM_21) -#define EXAMPLE_LCD_GPIO_DATA15 (GPIO_NUM_14) - -/* Touch settings */ -#define EXAMPLE_TOUCH_I2C_NUM (0) -#define EXAMPLE_TOUCH_I2C_CLK_HZ (400000) - -/* LCD touch pins */ -#define EXAMPLE_TOUCH_I2C_SCL (GPIO_NUM_18) -#define EXAMPLE_TOUCH_I2C_SDA (GPIO_NUM_17) - -#define EXAMPLE_LCD_PANEL_35HZ_RGB_TIMING() \ - { \ - .pclk_hz = 16 * 1000 * 1000, \ - .h_res = EXAMPLE_LCD_H_RES, \ - .v_res = EXAMPLE_LCD_V_RES, \ - .hsync_pulse_width = 4, \ - .hsync_back_porch = 8, \ - .hsync_front_porch = 8, \ - .vsync_pulse_width = 4, \ - .vsync_back_porch = 8, \ - .vsync_front_porch = 8, \ - .flags.pclk_active_neg = true, \ - .flags.hsync_idle_low =true, \ - } - - - -static const char *TAG = "domoTic"; - -extern char *upEvent; -extern char *downEvent; - - -// LVGL image declare -LV_IMG_DECLARE(esp_logo) - -/* LCD IO and panel */ -static esp_lcd_panel_handle_t lcd_panel = NULL; -static esp_lcd_touch_handle_t touch_handle = NULL; - -/* LVGL display and touch */ -static lv_display_t *lvgl_disp = NULL; -static lv_indev_t *lvgl_touch_indev = NULL; - -lv_obj_t *chart; -lv_chart_series_t *ser1; - -static esp_err_t app_lcd_init(void) -{ - esp_err_t ret = ESP_OK; - - /* LCD initialization */ - ESP_LOGI(TAG, "Initialize RGB panel"); - esp_lcd_rgb_panel_config_t panel_conf = { - .clk_src = LCD_CLK_SRC_PLL160M, - .psram_trans_align = 64, - .data_width = 16, - .bits_per_pixel = 16, - .de_gpio_num = EXAMPLE_LCD_GPIO_DE, - .pclk_gpio_num = EXAMPLE_LCD_GPIO_PCLK, - .vsync_gpio_num = EXAMPLE_LCD_GPIO_VSYNC, - .hsync_gpio_num = EXAMPLE_LCD_GPIO_HSYNC, - .disp_gpio_num = EXAMPLE_LCD_GPIO_DISP, - .data_gpio_nums = { - EXAMPLE_LCD_GPIO_DATA0, - EXAMPLE_LCD_GPIO_DATA1, - EXAMPLE_LCD_GPIO_DATA2, - EXAMPLE_LCD_GPIO_DATA3, - EXAMPLE_LCD_GPIO_DATA4, - EXAMPLE_LCD_GPIO_DATA5, - EXAMPLE_LCD_GPIO_DATA6, - EXAMPLE_LCD_GPIO_DATA7, - EXAMPLE_LCD_GPIO_DATA8, - EXAMPLE_LCD_GPIO_DATA9, - EXAMPLE_LCD_GPIO_DATA10, - EXAMPLE_LCD_GPIO_DATA11, - EXAMPLE_LCD_GPIO_DATA12, - EXAMPLE_LCD_GPIO_DATA13, - EXAMPLE_LCD_GPIO_DATA14, - EXAMPLE_LCD_GPIO_DATA15, - }, - .timings = EXAMPLE_LCD_PANEL_35HZ_RGB_TIMING(), - .flags.fb_in_psram = 1, - .num_fbs = EXAMPLE_LCD_RGB_BUFFER_NUMS, -#if EXAMPLE_LCD_RGB_BOUNCE_BUFFER_MODE - .bounce_buffer_size_px = EXAMPLE_LCD_H_RES * EXAMPLE_LCD_RGB_BOUNCE_BUFFER_HEIGHT, -#endif - }; - ESP_GOTO_ON_ERROR(esp_lcd_new_rgb_panel(&panel_conf, &lcd_panel), err, TAG, "RGB init failed"); - ESP_GOTO_ON_ERROR(esp_lcd_panel_init(lcd_panel), err, TAG, "LCD init failed"); - - return ret; - -err: - if (lcd_panel) - { - esp_lcd_panel_del(lcd_panel); - } - return ret; -} - -static esp_err_t app_touch_init(void) -{ - /* Initilize I2C */ - const i2c_config_t i2c_conf = { - .mode = I2C_MODE_MASTER, - .sda_io_num = EXAMPLE_TOUCH_I2C_SDA, - .sda_pullup_en = GPIO_PULLUP_DISABLE, - .scl_io_num = EXAMPLE_TOUCH_I2C_SCL, - .scl_pullup_en = GPIO_PULLUP_DISABLE, - .master.clk_speed = EXAMPLE_TOUCH_I2C_CLK_HZ}; - ESP_RETURN_ON_ERROR(i2c_param_config(EXAMPLE_TOUCH_I2C_NUM, &i2c_conf), TAG, "I2C configuration failed"); - ESP_RETURN_ON_ERROR(i2c_driver_install(EXAMPLE_TOUCH_I2C_NUM, i2c_conf.mode, 0, 0, 0), TAG, "I2C initialization failed"); - - /* Initialize touch HW */ - const esp_lcd_touch_config_t tp_cfg = { - .x_max = EXAMPLE_LCD_H_RES, - .y_max = EXAMPLE_LCD_V_RES, - .rst_gpio_num = GPIO_NUM_NC, - .int_gpio_num = GPIO_NUM_NC, - .levels = { - .reset = 0, - .interrupt = 0, - }, - .flags = { - .swap_xy = 0, - .mirror_x = 0, - .mirror_y = 0, - }, - }; - esp_lcd_panel_io_handle_t tp_io_handle = NULL; - const esp_lcd_panel_io_i2c_config_t tp_io_config = ESP_LCD_TOUCH_IO_I2C_GT911_CONFIG(); - ESP_RETURN_ON_ERROR(esp_lcd_new_panel_io_i2c((esp_lcd_i2c_bus_handle_t)EXAMPLE_TOUCH_I2C_NUM, &tp_io_config, &tp_io_handle), TAG, ""); - return esp_lcd_touch_new_i2c_gt911(tp_io_handle, &tp_cfg, &touch_handle); -} - -static esp_err_t app_lvgl_init(void) -{ - /* Initialize LVGL */ - const lvgl_port_cfg_t lvgl_cfg = { - .task_priority = 4, /* LVGL task priority */ - .task_stack = 12288,//6144, /* LVGL task stack size */ - .task_affinity = -1, /* LVGL task pinned to core (-1 is no affinity) */ - .task_max_sleep_ms = 500, /* Maximum sleep in LVGL task */ - .timer_period_ms = 5 /* LVGL timer tick period in ms */ - }; - ESP_RETURN_ON_ERROR(lvgl_port_init(&lvgl_cfg), TAG, "LVGL port initialization failed"); - - uint32_t buff_size = EXAMPLE_LCD_H_RES * EXAMPLE_LCD_DRAW_BUFF_HEIGHT; -#if EXAMPLE_LCD_LVGL_FULL_REFRESH || EXAMPLE_LCD_LVGL_DIRECT_MODE - buff_size = EXAMPLE_LCD_H_RES * EXAMPLE_LCD_V_RES; -#endif - - /* Add LCD screen */ - ESP_LOGD(TAG, "Add LCD screen"); - const lvgl_port_display_cfg_t disp_cfg = { - .panel_handle = lcd_panel, - .buffer_size = buff_size, - .double_buffer = EXAMPLE_LCD_DRAW_BUFF_DOUBLE, - .hres = EXAMPLE_LCD_H_RES, - .vres = EXAMPLE_LCD_V_RES, - .monochrome = false, -#if LVGL_VERSION_MAJOR >= 9 - .color_format = LV_COLOR_FORMAT_RGB565, -#endif - .rotation = { - .swap_xy = false, - .mirror_x = false, - .mirror_y = false, - }, - .flags = { - .buff_dma = false, - .buff_spiram = false, -#if EXAMPLE_LCD_LVGL_FULL_REFRESH - .full_refresh = true, -#elif EXAMPLE_LCD_LVGL_DIRECT_MODE - .direct_mode = true, -#endif -#if LVGL_VERSION_MAJOR >= 9 - .swap_bytes = false, -#endif - }}; - const lvgl_port_display_rgb_cfg_t rgb_cfg = { - .flags = { -#if EXAMPLE_LCD_RGB_BOUNCE_BUFFER_MODE - .bb_mode = true, -#else - .bb_mode = false, -#endif -#if EXAMPLE_LCD_LVGL_AVOID_TEAR - .avoid_tearing = true, -#else - .avoid_tearing = false, -#endif - }}; - lvgl_disp = lvgl_port_add_disp_rgb(&disp_cfg, &rgb_cfg); - - /* Add touch input (for selected screen) */ - const lvgl_port_touch_cfg_t touch_cfg = { - .disp = lvgl_disp, - .handle = touch_handle, - }; - lvgl_touch_indev = lvgl_port_add_touch(&touch_cfg); - - return ESP_OK; -} - -static void _app_button_cb(lv_event_t *e) -{ - if(lvgl_port_lock(0)){ - lv_disp_rotation_t rotation = lv_disp_get_rotation(lvgl_disp); - rotation++; - if (rotation > LV_DISPLAY_ROTATION_270) - { - rotation = LV_DISPLAY_ROTATION_0; - } - - /* LCD HW rotation */ - lv_disp_set_rotation(lvgl_disp, rotation); - lvgl_port_unlock(); - } -} - -lv_subject_t meteoStatus; - -static lv_style_t no_padding; -static lv_style_t style_font_18; - - -static void app_main_display(void) -{ - - lv_style_init(&no_padding); - lv_style_set_pad_all(&no_padding, 0); - - lv_style_init(&style_font_18); - lv_style_set_text_font(&style_font_18, &montserrat_medium_18); - - lv_obj_t *cont_status = lv_obj_create(lv_layer_top()); - lv_obj_add_style(cont_status,&no_padding,0); - lv_obj_align(cont_status,LV_ALIGN_TOP_RIGHT,0,0); - lv_obj_set_flex_flow(cont_status, LV_FLEX_FLOW_ROW); - lv_obj_set_height(cont_status,LV_SIZE_CONTENT); - lv_obj_set_width(cont_status,LV_SIZE_CONTENT); - - lv_obj_t *jour = lv_label_create(cont_status); - lv_obj_add_style(jour,&style_font_18,0); - - setlocale(LC_ALL, "fr_FR"); - char strftime_buf[64]; - time_t now = 0; - time(&now); - struct tm timeinfo = { 0 }; - localtime_r(&now, &timeinfo); - sprintf(strftime_buf,"%s %d %s", days[timeinfo.tm_wday], timeinfo.tm_mday, months[timeinfo.tm_mon]); - - lv_label_set_text(jour,strftime_buf); - - lv_obj_refr_size(cont_status); - //lv_obj_align(jour, LV_ALIGN_CENTER,0,0); - - lv_obj_t *meteoR = lv_label_create(cont_status); - lv_label_set_text(meteoR,"--"); - lv_label_bind_text(meteoR, &meteoStatus, "Meteo %d"); - - lv_obj_t *wifi = lv_image_create(cont_status); - //lv_obj_set_style_bg_color(wifi, lv_palette_darken(LV_PALETTE_GREY, 3), 0); - //lv_obj_set_style_border_width(wifi,1,0); - //lv_obj_set_style_border_color(wifi,lv_palette_darken(LV_PALETTE_GREY, 3),0); - //lv_label_set_text(wifi,"Wifi Ok"); - //lv_label_bind_text(wifi, &wifiStatus, "Wifi %d"); - - - lv_image_create(cont_status); - //lv_label_set_text(mqtt,"Mqtt Ok"); - //lv_label_bind_text(mqtt, &mqttStatus, "Mqtt %d"); - - lv_obj_t *scr = lv_scr_act(); - - /* Your LVGL objects code here .... */ - - /* Create image */ - lv_obj_t *img_logo = lv_img_create(scr); - lv_img_set_src(img_logo, &esp_logo); - lv_obj_align(img_logo, LV_ALIGN_TOP_MID, 0, 20); - - /* Label */ - lv_obj_t *label = lv_label_create(scr); - lv_obj_set_width(label, EXAMPLE_LCD_H_RES); - lv_obj_set_style_text_align(label, LV_TEXT_ALIGN_CENTER, 0); -#if LVGL_VERSION_MAJOR == 8 - lv_label_set_recolor(label, true); - lv_label_set_text(label, "#FF0000 " LV_SYMBOL_BELL " Hello world Espressif and LVGL " LV_SYMBOL_BELL "#\n#FF9400 " LV_SYMBOL_WARNING " For simplier initialization, use BSP " LV_SYMBOL_WARNING " #"); -#else - lv_label_set_text(label, LV_SYMBOL_BELL " Hello world Espressif and LVGL " LV_SYMBOL_BELL "\n " LV_SYMBOL_WARNING " For simplier initialization, use BSP " LV_SYMBOL_WARNING); -#endif - lv_obj_align(label, LV_ALIGN_CENTER, 0, 20); - - /* Button */ - lv_obj_t *btn = lv_btn_create(scr); - label = lv_label_create(btn); - lv_label_set_text_static(label, "Rotate screen"); - lv_obj_align(btn, LV_ALIGN_BOTTOM_MID, 0, -30); - lv_obj_add_event_cb(btn, _app_button_cb, LV_EVENT_CLICKED, NULL); -} - -char tempExtStr[6]; -char tempIntStr[6]; -char hauteurCuveStr[9]; -char hauteurCuveEvolStr[9]; -lv_subject_t tempIntSubj; -lv_subject_t tempExtSubj; -lv_subject_t hauteurCuveSubj; -lv_subject_t hauteurCuveEvolSubj; -lv_subject_t forecastD1Subj; -lv_subject_t forecastD2Subj; -lv_subject_t forecastD3Subj; -lv_subject_t *tmpSubj[3] = {&forecastD1Subj, &forecastD2Subj, &forecastD3Subj}; -lv_subject_t forecastH1Subj; -lv_subject_t forecastH2Subj; -lv_subject_t forecastH3Subj; -lv_subject_t *tmpHSubj[3] = {&forecastH1Subj, &forecastH2Subj, &forecastH3Subj}; - - -extern esp_mqtt_client_handle_t client; - -static void event_handler(lv_event_t *e) -{ - lv_event_code_t code = lv_event_get_code(e); - //lv_obj_t *obj = (lv_obj_t *)lv_event_get_target(e); - char *evtData = (char *)lv_event_get_user_data(e); - - switch (code) - { - case LV_EVENT_PRESSED: - // LV_LOG_USER("%s was pressed\n", evtData); - break; - case LV_EVENT_CLICKED: - ESP_LOGI(TAG, "%s was clicked\n", evtData); - esp_mqtt_client_publish(client, "volets", evtData, 0, 0, 0); - break; - case LV_EVENT_LONG_PRESSED: - LV_LOG_USER("%s was long pressed\n", evtData); - break; - case LV_EVENT_LONG_PRESSED_REPEAT: - LV_LOG_USER("%s was long press repeat\n", evtData); - break; - default: - break; - } -} -LV_IMAGE_DECLARE(plan_rdc); -LV_IMAGE_DECLARE(plan_etage); -/* -LV_IMAGE_DECLARE(p1j); -LV_IMAGE_DECLARE(p2j); -LV_IMAGE_DECLARE(p3j); -LV_IMAGE_DECLARE(p4j); -LV_IMAGE_DECLARE(p5bisj); -LV_IMAGE_DECLARE(p12j); -LV_IMAGE_DECLARE(p12bisj); -LV_IMAGE_DECLARE(p13j); -LV_IMAGE_DECLARE(p13bisj); -LV_IMAGE_DECLARE(p14j); -LV_IMAGE_DECLARE(p24j); -LV_IMAGE_DECLARE(p25j); -LV_IMAGE_DECLARE(p26j); -LV_IMAGE_DECLARE(p27j); -LV_IMAGE_DECLARE(p28j); -LV_IMAGE_DECLARE(p29j); -*/ - -struct lv_observer_t { - lv_subject_t * subject; /**< The observed value */ - lv_observer_cb_t cb; /**< Callback that should be called when the value changes*/ - void * target; /**< A target for the observer, e.g. a widget or style*/ - void * user_data; /**< Additional parameter supplied when subscribing*/ - uint32_t auto_free_user_data : 1; /**< Automatically free user data when the observer is removed */ - uint32_t notified : 1; /**< Mark if this observer was already notified*/ - uint32_t for_obj : 1; /**< `target` is an `lv_obj_t *`*/ -}; - -static lv_style_t style_container; -static lv_style_t style_font_24; -static lv_style_t style_font_12; - -// Callback pour mettre à jour une météo journaliere -// On pointe sur un tableau de meteodailyforecast_data -static void weatherdata_obs_cb(lv_observer_t *observer, lv_subject_t *subject) -{ - - ESP_LOGE(TAG, "CB meteo jour declenché"); - // Retrieve weatherdata - const struct meteodailyforecast_data *data = subject->value.pointer; - //printffd(data); - //char buff[40] = {}; - // sprintf(buff,"%s %.1f %.1f", data->previsions.desc, data->previsions.min, data->previsions.max); - - lv_obj_t *parent = (lv_obj_t *)(observer->target); - lv_obj_t *datefld = lv_obj_get_child(parent, 0); - lv_obj_t *desc_icon = lv_obj_get_child(parent, 1); - lv_obj_t *temps = lv_obj_get_child(parent, 2); - showMeteoIcon(data->previsions.icon, desc_icon,0); - char buffer[80]; - dtToString(data->datetime,buffer); - - lv_label_set_text(datefld, buffer); - lv_label_set_text(lv_obj_get_child(desc_icon, 1), data->previsions.desc); - lv_label_set_text_fmt(lv_obj_get_child(temps, 0), "%.1f°C", data->previsions.max); - lv_label_set_text_fmt(lv_obj_get_child(temps, 1), "%.1f°C", data->previsions.min); -} - -// Callback pour mettre à jour une météo horaire -// On pointe sur un tableau de meteoforecast_data -static void weatherdataH_obs_cb(lv_observer_t *observer, lv_subject_t *subject) -{ - ESP_LOGE(TAG, "CB meteo horaire declenché"); - // Retrieve weatherdata - const struct meteoforecast_data *data = subject->value.pointer; - //printffd(data); - //char buff[40] = {}; - // sprintf(buff,"%s %.1f %.1f", data->previsions.desc, data->previsions.min, data->previsions.max); - - lv_obj_t *parent = (lv_obj_t *)(observer->target); - lv_obj_t *datefld = lv_obj_get_child(parent, 0); - lv_obj_t *temp_desc_icon = lv_obj_get_child(parent, 1); - showMeteoIcon(data->previsions.icon, temp_desc_icon, 1); - - char buffer[80]; - dtHToString(data->datetime,buffer); - - lv_label_set_text(datefld, buffer); - lv_label_set_text(lv_obj_get_child(temp_desc_icon, 2), data->previsions.desc); - lv_label_set_text_fmt(lv_obj_get_child(temp_desc_icon, 0), "%.1f°C", data->previsions.value); -} - -void showMeteoIcon(const char *icon, lv_obj_t *desc_icon, int childNr) -{ - lv_obj_t* img = lv_obj_get_child(desc_icon, childNr); - char *str1= "A:/littlefs/"; - char* result = malloc(strlen(str1) + strlen(icon) + 6); - sprintf(result, "%s%s.png", str1, icon); - lv_image_set_src(img, result); - /* - if (strcmp(icon, "p1j") == 0) - { - lv_image_set_src(img, &p1j); - } - else if (strcmp(icon, "p2j") == 0) - { - lv_image_set_src(img, &p2j); - } - else if (strcmp(icon, "p3j") == 0) - { - lv_image_set_src(img, &p3j); - } - else if (strcmp(icon, "p4j") == 0) - { - lv_image_set_src(img, &p4j); - } - else if (strcmp(icon, "p5bisj") == 0) - { - lv_image_set_src(img, &p5bisj); - } - else if (strcmp(icon, "p12j") == 0) - { - lv_image_set_src(img, &p12j); - } - else if (strcmp(icon, "p12bisj") == 0) - { - lv_image_set_src(img, &p12bisj); - } - else if (strcmp(icon, "p13j") == 0) - { - lv_image_set_src(img, &p13j); - } - else if (strcmp(icon, "p13bisj") == 0) - { - lv_image_set_src(img, &p13bisj); - } - else if (strcmp(icon, "p14j") == 0) - { - lv_image_set_src(img, &p14j); - } - else if (strcmp(icon, "p24j") == 0) - { - lv_image_set_src(img, &p24j); - } - else if (strcmp(icon, "p25j") == 0) - { - lv_image_set_src(img, &p25j); - } - else if (strcmp(icon, "p26j") == 0) - { - lv_image_set_src(img, &p26j); - } - else if (strcmp(icon, "p27j") == 0) - { - lv_image_set_src(img, &p27j); - } - else if (strcmp(icon, "p28j") == 0) - { - lv_image_set_src(img, &p28j); - } - else if (strcmp(icon, "p29j") == 0) - { - lv_image_set_src(img, &p29j); - } - else - { - ESP_LOGE(TAG, "Image %s non connue", icon); - } - */ -} -/* ------------------------------------------------------------ */ -/* Fragment meteo journaliere (date,icone, min et max) */ -/* ------------------------------------------------------------ */ - -// Structure meteo journaliere -struct weatherDay_fragment_t -{ - /* IMPORTANT: don't miss this part */ - lv_fragment_t base; - /* States, object references and data fields for this fragment */ - int dayNr; - bool showTitle; - const char *title; - float minTemp; - float maxTemp; -}; - -//Constructeur meteo journaliere -static void weatherDay_fragment_ctor(lv_fragment_t *self, void * args) -{ - int dayNo = ((int *)args)[0]; - bool showDate = ((int*)args)[1]; - ((struct weatherDay_fragment_t *)self)->dayNr = dayNo; - ((struct weatherDay_fragment_t *)self)->showTitle = showDate; - ESP_LOGI(TAG, "Fragment initialisé avec le jour n°%d - Afficher la date %d",dayNo, showDate); -} - -// Ce fragment affiche une prévision journaliere (date,icone, min et max) -static lv_obj_t *weatherDay_fragment_create_obj(lv_fragment_t *self, lv_obj_t *parent) -{ - - - lv_obj_t *sup = lv_obj_create(parent); - - lv_obj_t *title = lv_label_create(sup); - lv_label_set_text(title, "--"); - - - lv_obj_set_flex_flow(sup, LV_FLEX_FLOW_ROW); - lv_obj_add_style(sup, &style_container, 0); - lv_obj_set_size(sup, LV_SIZE_CONTENT, LV_SIZE_CONTENT); - - - lv_obj_t *container = lv_obj_create(sup); - lv_obj_set_flex_flow(container, LV_FLEX_FLOW_COLUMN); - lv_obj_set_flex_align(container,LV_FLEX_ALIGN_CENTER,LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); - lv_obj_add_style(container, &no_padding, 0); - lv_obj_set_width(container, 100); - lv_obj_set_height(container, 80); - - lv_obj_t *img1 = lv_image_create(container); - lv_obj_add_style(img1, &no_padding, 0); - lv_obj_set_style_bg_color(img1,lv_palette_lighten(LV_PALETTE_BLUE_GREY, 4),0); - lv_image_set_inner_align(img1, LV_IMAGE_ALIGN_TOP_LEFT); - lv_image_set_offset_y(img1, -8); - lv_image_set_offset_x(img1, -5); - lv_obj_set_size(img1,40,32); - lv_image_set_src(img1,LV_SYMBOL_DUMMY); - //lv_obj_set_style_border_width(img1,2,0); - //lv_obj_set_style_border_color(img1, lv_palette_main(LV_PALETTE_BLUE_GREY), 0); - lv_obj_align(img1, LV_ALIGN_CENTER, 0, 0); - - lv_obj_t *desc = lv_label_create(container); - lv_label_set_text(desc,"--"); - lv_obj_add_style(desc, &style_font_12, 0); - - lv_obj_t *container2 = lv_obj_create(sup); - lv_obj_set_width(container2, LV_SIZE_CONTENT); - lv_obj_set_height(container2, 80); - lv_obj_add_style(container2, &no_padding, 0); - lv_obj_set_style_pad_top(container2,5,0); - lv_obj_set_style_pad_bottom(container2,5,0); - lv_obj_set_flex_flow(container2, LV_FLEX_FLOW_COLUMN); - lv_obj_set_flex_align(container2, LV_FLEX_ALIGN_SPACE_BETWEEN, LV_FLEX_ALIGN_START, LV_FLEX_ALIGN_START); - - static lv_style_t tempStyle; - lv_style_init(&tempStyle); - //lv_style_set_text_font(&tempStyle,¬omedium16); - - lv_obj_t *max = lv_label_create(container2); - lv_label_set_text(max,"--"); - lv_obj_add_style(max, &tempStyle,0); - lv_obj_add_style(max, &style_font_18, 0); - lv_obj_set_style_text_color(max,lv_color_hex(0xFF0000),0); - lv_obj_add_style(max, &style_font_18, 0); - - lv_obj_t *min = lv_label_create(container2); - lv_label_set_text(min,"--"); - lv_obj_add_style(min, &tempStyle,0); - lv_obj_add_style(min, &style_font_18, 0); - lv_obj_set_style_text_color(min,lv_color_hex(0x3000FF),0); - lv_obj_add_style(min, &style_font_18, 0); - - // On positionne un observer sur le subjet correspondant au jour du widget - lv_subject_add_observer_obj(tmpSubj[((struct weatherDay_fragment_t *)self)->dayNr], weatherdata_obs_cb, sup, NULL); - return container; -} - -// Fragment meteo journaliere -const lv_fragment_class_t meteoFragment = { - /* Initialize something needed */ - .constructor_cb = weatherDay_fragment_ctor, - /* Create view objects */ - .create_obj_cb = weatherDay_fragment_create_obj, - /* IMPORTANT: size of your fragment struct */ - .instance_size = sizeof(struct weatherDay_fragment_t), -}; - -/* ------------------------------------------------------------ */ -/* Fragment meteo horaire ("heure",icone, temp) */ -/* ------------------------------------------------------------ */ - -// Structure meteo horaire -struct weatherH_fragment_t -{ - /* IMPORTANT: don't miss this part */ - lv_fragment_t base; - /* States, object references and data fields for this fragment */ - int horaireNr; - bool showTitle; - const char *horaire; - float temp; -}; - -//Constructeur meteo horaire -static void weatherH_fragment_ctor(lv_fragment_t *self, void * args) -{ - // Represente le n° (index dans le tableau) a afficher - int horaireNr = ((int *)args)[0]; - bool showDate = ((int*)args)[1]; - ((struct weatherH_fragment_t *)self)->horaireNr = horaireNr; - ((struct weatherH_fragment_t *)self)->showTitle = showDate; - ESP_LOGI(TAG, "Fragment initialisé avec l'horaire %d",horaireNr); -} - -// Ce fragment affiche une prévision horaire (date,icone, temp moyenne) -static lv_obj_t *weatherH_fragment_create_obj(lv_fragment_t *self, lv_obj_t *parent) -{ - - - lv_obj_t *sup = lv_obj_create(parent); - - lv_obj_t *title = lv_label_create(sup); - lv_label_set_text(title, "--"); - - - lv_obj_set_flex_flow(sup, LV_FLEX_FLOW_ROW); - lv_obj_add_style(sup, &style_container, 0); - lv_obj_set_size(sup, LV_SIZE_CONTENT, LV_SIZE_CONTENT); - - - lv_obj_t *container = lv_obj_create(sup); - lv_obj_set_flex_flow(container, LV_FLEX_FLOW_COLUMN); - lv_obj_set_flex_align(container,LV_FLEX_ALIGN_CENTER,LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); - lv_obj_add_style(container, &no_padding, 0); - lv_obj_set_width(container, 100); - lv_obj_set_height(container, LV_SIZE_CONTENT); - - static lv_style_t tempStyle; - lv_style_init(&tempStyle); - //lv_style_set_text_font(&tempStyle,¬omedium16); - - lv_obj_t *temp = lv_label_create(container); - lv_label_set_text(temp,"--"); - lv_obj_add_style(temp, &tempStyle,0); - lv_obj_add_style(temp, &style_font_18, 0); - //lv_obj_set_style_text_color(temp,lv_color_hex(0xFF0000),0); - lv_obj_add_style(temp, &style_font_18, 0); - - lv_obj_t *img1 = lv_image_create(container); - lv_obj_add_style(img1, &no_padding, 0); - lv_obj_set_style_bg_color(img1,lv_palette_lighten(LV_PALETTE_BLUE_GREY, 4),0); - lv_image_set_inner_align(img1, LV_IMAGE_ALIGN_TOP_LEFT); - lv_image_set_offset_y(img1, -8); - lv_image_set_offset_x(img1, -5); - lv_obj_set_size(img1,40,32); - lv_image_set_src(img1,LV_SYMBOL_DUMMY); - //lv_obj_set_style_border_width(img1,2,0); - //lv_obj_set_style_border_color(img1, lv_palette_main(LV_PALETTE_BLUE_GREY), 0); - lv_obj_align(img1, LV_ALIGN_CENTER, 0, 0); - - lv_obj_t *desc = lv_label_create(container); - lv_label_set_text(desc,"--"); - lv_obj_add_style(desc, &style_font_12, 0); - - // On positionne un observer sur le subjet correspondant a l'horaire du widget - ESP_LOGE(TAG, "on positionne obs sur horaire %d", ((struct weatherH_fragment_t *)self)->horaireNr); - lv_subject_add_observer_obj(tmpHSubj[((struct weatherH_fragment_t *)self)->horaireNr], weatherdataH_obs_cb, sup, NULL); - return container; -} - -// Fragment meteo horaire -const lv_fragment_class_t meteoHFragment = { - /* Initialize something needed */ - .constructor_cb = weatherH_fragment_ctor, - /* Create view objects */ - .create_obj_cb = weatherH_fragment_create_obj, - /* IMPORTANT: size of your fragment struct */ - .instance_size = sizeof(struct weatherH_fragment_t), -}; - -/* -------------------------------------------------------------- */ -/* Fragment 3 meteo "jour" (aujourd'hui, demain, apres demain) */ -/* -------------------------------------------------------------- */ -struct meteodailyforecast_fragment_t { - /* IMPORTANT: don't miss this part */ - lv_fragment_t base; - /* States, object references and data fields for this fragment */ - const char *title; - bool showDate; -}; - -static void meteodailyforecast_fragment_ctor(lv_fragment_t * self, void * args){ - struct meteodailyforecast_fragment_t *myself=((struct meteodailyforecast_fragment_t *) self); - myself->showDate = args; -} - -static lv_obj_t * meteodailyforecast_fragment_create_obj(lv_fragment_t * self, lv_obj_t * parent) -{ - - lv_fragment_manager_t *manager = lv_fragment_manager_create(NULL); - - int args[2]={0,((struct meteodailyforecast_fragment_t*)self)->showDate}; - lv_fragment_t *fragment = lv_fragment_create(&meteoFragment, args); - lv_fragment_manager_add(manager, fragment, &parent); - - args[0]=1; - fragment = lv_fragment_create(&meteoFragment, args); - lv_fragment_manager_add(manager, fragment, &parent); - - args[0]=2; - fragment = lv_fragment_create(&meteoFragment, args); - lv_fragment_manager_add(manager, fragment, &parent); - - return parent; -} - - - -const lv_fragment_class_t meteodailyforecast_cls = { - /* Initialize something needed */ - .constructor_cb = meteodailyforecast_fragment_ctor, - /* Create view objects */ - .create_obj_cb = meteodailyforecast_fragment_create_obj, - /* IMPORTANT: size of your fragment struct */ - .instance_size = sizeof(struct meteodailyforecast_fragment_t), -}; -/* -------------------------------------------------------------------------------- */ -/* Fragment 3 meteo "horaire" - matin/midi/soir (icone, temp moyenne) */ -/* -------------------------------------------------------------------------------- */ - -struct meteoforecast_fragment_t { - /* IMPORTANT: don't miss this part */ - lv_fragment_t base; - /* States, object references and data fields for this fragment */ - const char *title; - bool showDate; -}; - -static void meteoforecast_fragment_ctor(lv_fragment_t * self, void * args){ - struct meteoforecast_fragment_t *myself=((struct meteoforecast_fragment_t *) self); - myself->showDate = args; -} - -static lv_obj_t * meteoforecast_fragment_create_obj(lv_fragment_t * self, lv_obj_t * parent) -{ - - lv_fragment_manager_t *manager = lv_fragment_manager_create(NULL); - - // On affiche 3 fragment meteo. 1 pour chaque "horaire" - int args[2]={0,((struct meteoforecast_fragment_t*)self)->showDate}; - lv_fragment_t *fragment = lv_fragment_create(&meteoHFragment, args); - lv_fragment_manager_add(manager, fragment, &parent); - - args[0]=1; - fragment = lv_fragment_create(&meteoHFragment, args); - lv_fragment_manager_add(manager, fragment, &parent); - - args[0]=2; - fragment = lv_fragment_create(&meteoHFragment, args); - lv_fragment_manager_add(manager, fragment, &parent); - - return parent; -} - -const lv_fragment_class_t meteoforecast_cls = { - /* Initialize something needed */ - .constructor_cb = meteoforecast_fragment_ctor, - /* Create view objects */ - .create_obj_cb = meteoforecast_fragment_create_obj, - /* IMPORTANT: size of your fragment struct */ - .instance_size = sizeof(struct meteoforecast_fragment_t), -}; - -struct lv_event_t { - void * current_target; - void * original_target; - lv_event_code_t code; - void * user_data; - void * param; - lv_event_t * prev; - uint8_t deleted : 1; - uint8_t stop_processing : 1; - uint8_t stop_bubbling : 1; -}; - -lv_obj_t * tab1; -lv_obj_t * tab2b; -lv_obj_t * tab3; -lv_obj_t * tab4; - -static void tabChgEvt(lv_event_t * event) -{ - uint32_t tabNr = lv_tabview_get_tab_active(event->user_data); - printf("Tab change %lu\n", tabNr); - switch (tabNr) - { - case 1: - lv_obj_t * tab2=lv_obj_create(tab2b); - lv_obj_set_flex_flow(tab2, LV_FLEX_FLOW_COLUMN); - lv_obj_add_style(tab2,&no_padding,0); - - lv_obj_set_size(tab2, lv_pct(85),lv_pct(100)); - lv_obj_t * cont_rdc=lv_obj_create(tab2); - lv_obj_set_size(cont_rdc,lv_pct(100), lv_pct(100)); - lv_obj_add_style(cont_rdc,&no_padding,0); - lv_obj_add_style(tab2,&no_padding,0); - lv_point_t positions_rdc[]={ - {5,105}, - {55,45}, - {110,20}, - {155,25}, - {225,45}, - {275,115}, - {295,185}}; - lv_obj_t * img=lv_image_create(cont_rdc); - lv_img_set_src(img, &plan_rdc); - float coef=1.5; - for (size_t i = 1; i < 8; i++) - { - lv_obj_t * btnVolet = lv_checkbox_create(cont_rdc); - lv_obj_set_pos(btnVolet,positions_rdc[i-1].x*coef,positions_rdc[i-1].y*coef); - lv_obj_add_style(btnVolet,&style_font_24,0); - //lv_obj_set_size(btnVolet,100,24); - - //char *nom[10]; - //sprintf(nom,"%d", i); - lv_checkbox_set_text(btnVolet,""); - } - - - lv_obj_t * cont_btn_volets=lv_obj_create(tab2b); - lv_obj_add_style(cont_btn_volets,&no_padding,0); - lv_obj_set_size(cont_btn_volets,lv_pct(15), lv_pct(100)); - - lv_obj_set_layout(cont_btn_volets, LV_LAYOUT_GRID); - static int32_t column_dsc[] = {LV_GRID_CONTENT, LV_GRID_TEMPLATE_LAST}; /*2 columns */ - static int32_t row_dsc[] = {LV_GRID_FR(1),LV_GRID_FR(1),LV_GRID_FR(1),LV_GRID_FR(1),LV_GRID_FR(1),LV_GRID_FR(1), LV_GRID_TEMPLATE_LAST}; - lv_obj_set_grid_dsc_array(cont_btn_volets, column_dsc, row_dsc); - - lv_obj_t * btnUp_bis = lv_button_create(cont_btn_volets); - lv_obj_t * lblButtonUp = lv_label_create(btnUp_bis); - lv_label_set_text(lblButtonUp,LV_SYMBOL_UP); - - lv_obj_t * btnDwn_bis = lv_button_create(cont_btn_volets); - lv_obj_t * lblButtonDwn = lv_label_create(btnDwn_bis); - lv_label_set_text(lblButtonDwn,LV_SYMBOL_DOWN); - - lv_obj_set_grid_cell(btnUp_bis, LV_GRID_ALIGN_STRETCH, 0, 1, - LV_GRID_ALIGN_STRETCH, 0, 1); - lv_obj_set_grid_cell(btnDwn_bis, LV_GRID_ALIGN_STRETCH, 0, 1, - LV_GRID_ALIGN_STRETCH, 1, 1); - - lv_obj_t * cont_etage=lv_obj_create(tab2); - lv_obj_set_size(cont_etage,lv_pct(100), lv_pct(100)); - lv_obj_add_style(cont_etage,&no_padding,0); - - img=lv_image_create(cont_etage); - lv_img_set_src(img, &plan_etage); - - lv_point_t positions_etage[]={ - {100,15}, - {250,15}, - {400,15}, - {480,300}, - {460,360}, - {320,415}}; - for (size_t i = 1; i < 7; i++) - { - lv_obj_t * btnVolet = lv_checkbox_create(cont_etage); - lv_obj_set_pos(btnVolet,positions_etage[i-1].x,positions_etage[i-1].y); - lv_obj_add_style(btnVolet,&style_font_24,0); - //lv_obj_set_size(btnVolet,100,24); - - //char *nom[10]; - //sprintf(nom,"%d", i); - lv_checkbox_set_text(btnVolet,""); - } - case 2: // Onglet Météo - lv_fragment_manager_t *manager2 = lv_fragment_manager_create(NULL); - lv_fragment_t *fragment2 = lv_fragment_create(&meteodailyforecast_cls, (void *)1); - lv_fragment_manager_add(manager2, fragment2, &tab3); - break; - - case 3: // Onglet températures - lv_obj_t * imgGraf = lv_image_create(tab4); - lv_image_set_src(imgGraf, "A:/sdcard/hello2.png"); - break; - - default: - break; - } - - -} - -/* ------------------------------------------------------------ */ -/* Dessin IHM */ -/* ------------------------------------------------------------ */ -void draw_ihm() -{ - lv_subject_init_string(&tempExtSubj, tempExtStr, NULL, 6, "--"); - lv_subject_init_string(&tempIntSubj, tempIntStr, NULL, 6, "--"); - lv_subject_init_string(&hauteurCuveSubj, hauteurCuveStr, NULL, 9, "--"); - lv_subject_init_string(&hauteurCuveEvolSubj, hauteurCuveEvolStr, NULL, 9, "--"); - - struct meteodailyforecast_data d; - struct dailyforecast_prev p; - lv_strcpy(p.desc,""); - d.previsions = p; - lv_subject_init_pointer(&forecastD1Subj, &d); - lv_subject_init_pointer(&forecastD2Subj, &d); - lv_subject_init_pointer(&forecastD3Subj, &d); - - struct meteoforecast_data d1; - struct forecast_prev p1; - lv_strcpy(p1.desc,""); - - d1.previsions = p1; - lv_subject_init_pointer(&forecastH1Subj, &d1); - lv_subject_init_pointer(&forecastH2Subj, &d1); - lv_subject_init_pointer(&forecastH3Subj, &d1); - - // keys.clear(); - lv_obj_clean(lv_scr_act()); - - /*Create a Tab view object*/ - lv_obj_t * tabview; - tabview = lv_tabview_create(lv_screen_active()); - lv_tabview_set_tab_bar_position(tabview, LV_DIR_LEFT); - lv_tabview_set_tab_bar_size(tabview, 80); - lv_obj_add_event_cb(tabview, tabChgEvt, LV_EVENT_VALUE_CHANGED, tabview); /* Assign an event callback */ - - lv_obj_set_style_bg_color(tabview, lv_palette_lighten(LV_PALETTE_RED, 2), 0); - - - lv_obj_t * tab_buttons = lv_tabview_get_tab_bar(tabview); - lv_obj_set_width(tab_buttons,100); - lv_obj_set_style_text_font(tab_buttons, &montserrat_medium_18, 0); - lv_obj_set_style_bg_color(tab_buttons, lv_palette_darken(LV_PALETTE_GREY, 3), 0); - lv_obj_set_style_text_color(tab_buttons, lv_palette_lighten(LV_PALETTE_GREY, 5), 0); - lv_obj_set_style_border_side(tab_buttons, LV_BORDER_SIDE_RIGHT, LV_PART_ITEMS | LV_STATE_CHECKED); - - /*Add 3 tabs (the tabs are page (lv_page) and can be scrolled*/ - tab1 = lv_tabview_add_tab(tabview, LV_SYMBOL_HOME); - tab2b = lv_tabview_add_tab(tabview, "Volets"); - tab3 = lv_tabview_add_tab(tabview, "Météo"); - tab4 = lv_tabview_add_tab(tabview, "Températures"); - /*lv_obj_t * tab5 = */lv_tabview_add_tab(tabview, "Cuve"); - - - lv_obj_set_style_bg_color(tab2b, lv_palette_lighten(LV_PALETTE_AMBER, 3), 0); - lv_obj_set_style_bg_opa(tab2b, LV_OPA_COVER, 0); - - - static lv_style_t style_btn; - lv_style_init(&style_btn); - - - lv_style_init(&style_font_24); - lv_style_set_text_font(&style_font_24, &montserrat_medium_24); - - lv_style_init(&style_font_12); - lv_style_set_text_font(&style_font_12, &montserrat_medium_12); - - // lv_style_set_bg_color(&style_btn, lv_color_hex(0x115588)); - // lv_style_set_bg_opa(&style_btn, LV_OPA_50); - // lv_style_set_border_width(&style_btn, 2); - // lv_style_set_border_color(&style_btn, lv_color_black()); - lv_style_set_width(&style_btn, 80); - lv_style_set_height(&style_btn, 100); - - // Un style pour les conteneurs (température, cuve ...) - lv_style_init(&style_container); - lv_style_set_pad_all(&style_container, 5); - // lv_style_set_height(&style_container,LV_SIZE_CONTENT); - lv_style_set_height(&style_container, 80); - lv_style_set_width(&style_container, 200); - lv_style_set_bg_color(&style_container, lv_palette_lighten(LV_PALETTE_BLUE_GREY, 4)); - lv_style_set_align(&style_container, LV_ALIGN_BOTTOM_LEFT); - lv_style_set_flex_cross_place(&style_container, LV_FLEX_ALIGN_END); - - static lv_style_t no_padding; - lv_style_init(&no_padding); - lv_style_set_pad_all(&no_padding, 0); - - static lv_style_t style_lbvValue; - lv_style_init(&style_lbvValue); - lv_style_set_text_font(&style_lbvValue, &lv_font_montserrat_40); - - lv_obj_t *supmain = tab1; - lv_obj_set_flex_flow(supmain, LV_FLEX_FLOW_COLUMN); - - lv_obj_t *main = lv_obj_create(supmain); - lv_obj_add_style(main,&no_padding,0); - lv_obj_set_size(main,LV_SIZE_CONTENT,LV_SIZE_CONTENT); - - lv_obj_set_flex_flow(main, LV_FLEX_FLOW_ROW); - lv_obj_set_style_pad_column(main, 1, 0); - - /*Create a container with COLUMN flex direction*/ - lv_obj_t *cont_col = lv_obj_create(main); - lv_obj_set_style_pad_all(cont_col, 5, 0); - lv_obj_set_size(cont_col, 250, 400); - lv_obj_align(cont_col, LV_ALIGN_TOP_LEFT, 0, 0); - lv_obj_set_flex_flow(cont_col, LV_FLEX_FLOW_COLUMN); - lv_obj_set_flex_align(cont_col,LV_FLEX_ALIGN_CENTER,LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); - - /*Create a container with COLUMN flex direction*/ - lv_obj_t *cont_col2 = lv_obj_create(main); - lv_obj_set_style_pad_all(cont_col2, 5, 0); - lv_obj_set_flex_align(cont_col2, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); - - /*Create a container with COLUMN flex direction*/ - lv_obj_t *cont_col3 = lv_obj_create(main); - lv_obj_set_style_pad_all(cont_col3, 5, 0); - lv_obj_set_size(cont_col3, 300, 400); - lv_obj_set_flex_flow(cont_col3, LV_FLEX_FLOW_COLUMN); - lv_obj_set_flex_align(cont_col3, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); - - lv_obj_set_height(cont_col2, 400); - lv_obj_set_width(cont_col2, LV_SIZE_CONTENT); - lv_obj_align_to(cont_col2, cont_col, LV_ALIGN_OUT_TOP_RIGHT, 0, 0); - lv_obj_set_flex_flow(cont_col2, LV_FLEX_FLOW_COLUMN); - - lv_obj_t *label1 = lv_label_create(cont_col); - lv_obj_set_style_text_font(label1, &montserrat_medium_18,0); - lv_label_set_text(label1, "Températures"); - lv_obj_set_pos(label1, 0, 0); - - /*Create a container with COLUMN flex direction*/ - lv_obj_t *cont_tempExt = lv_obj_create(cont_col); - lv_obj_add_style(cont_tempExt, &style_container, 0); - // lv_obj_set_height(cont_tempExt,50); - lv_obj_set_flex_flow(cont_tempExt, LV_FLEX_FLOW_ROW); - lv_obj_t *lblExt = lv_label_create(cont_tempExt); - lv_label_set_text(lblExt, "ext."); - lv_obj_t *lblTempExt = lv_label_create(cont_tempExt); - lv_obj_add_style(lblTempExt, &style_lbvValue, 0); - lv_label_set_text(lblTempExt, ""); - lv_label_bind_text(lblTempExt, &tempExtSubj, "%s °C"); - - /*Create a container with COLUMN flex direction*/ - lv_obj_t *cont_tempInt = lv_obj_create(cont_col); - lv_obj_add_style(cont_tempInt, &style_container, 0); - // lv_obj_set_height(cont_tempInt,50); - lv_obj_set_flex_flow(cont_tempInt, LV_FLEX_FLOW_ROW); - lv_obj_t *lblInt = lv_label_create(cont_tempInt); - lv_label_set_text(lblInt, "int."); - lv_obj_t *lblTempInt = lv_label_create(cont_tempInt); - lv_obj_add_style(lblTempInt, &style_lbvValue, 0); - lv_label_set_text(lblTempInt, ""); - lv_label_bind_text(lblTempInt, &tempIntSubj, "%s °C"); - - /*Create a container with COLUMN flex direction*/ - lv_obj_t *cont_Cuve = lv_obj_create(cont_col); - lv_obj_add_style(cont_Cuve, &style_container, 0); - lv_obj_set_flex_flow(cont_Cuve, LV_FLEX_FLOW_ROW_WRAP); - // lv_obj_set_height(cont_Cuve,80); - - lv_obj_t *lblHauteurEau = lv_label_create(cont_Cuve); - lv_label_set_text(lblHauteurEau, "Cuve: "); - lv_obj_t *lblHauteurCuve = lv_label_create(cont_Cuve); - lv_obj_add_style(lblHauteurCuve, &style_lbvValue, 0); - lv_label_bind_text(lblHauteurCuve, &hauteurCuveSubj, "%s cm"); - - lv_obj_t *btnUp = lv_button_create(cont_col2); - lv_obj_add_style(btnUp, &style_btn, 0); - lv_obj_add_event_cb(btnUp, event_handler, LV_EVENT_ALL, upEvent); - lv_obj_align(btnUp, LV_ALIGN_CENTER, 0, -40); - lv_obj_remove_flag(btnUp, LV_OBJ_FLAG_PRESS_LOCK); - lv_obj_t *label = lv_label_create(btnUp); - lv_obj_add_style(label, &style_lbvValue, 0); - lv_label_set_text(label, LV_SYMBOL_UP); - lv_obj_center(label); - - lv_obj_t *btnDwn = lv_button_create(cont_col2); - lv_obj_add_style(btnDwn, &style_btn, 0); - lv_obj_add_event_cb(btnDwn, event_handler, LV_EVENT_ALL, downEvent); - lv_obj_align(btnDwn, LV_ALIGN_CENTER, 0, -40); - lv_obj_remove_flag(btnDwn, LV_OBJ_FLAG_PRESS_LOCK); - label = lv_label_create(btnDwn); - lv_obj_add_style(label, &style_lbvValue, 0); - lv_label_set_text(label, LV_SYMBOL_DOWN); - lv_obj_center(label); - - lv_fragment_manager_t *manager = lv_fragment_manager_create(NULL); - lv_fragment_t *fragment = lv_fragment_create(&meteoforecast_cls, 0); - lv_fragment_manager_add(manager, fragment, &cont_col3); - - - lv_obj_set_flex_flow(tab2b, LV_FLEX_FLOW_ROW); - - - lv_obj_set_flex_flow(tab3, LV_FLEX_FLOW_COLUMN); - -} - -void weather_data_retreived_start() -{ - if(lvgl_port_lock(0)){ - lv_subject_set_int(&meteoStatus,1); - lvgl_port_unlock(); - } -} - -void weather_data_retreived(struct meteodailyforecast_data dailyDatas[3], struct meteoforecast_data datas[3]) -{ - /* - ESP_LOGE(TAG, "debut debug"); - printf("%lld\n", datas[0].datetime); - printf("%s\n", datas[0].previsions.desc); - printf("%f\n", datas[0].previsions.min); - printf("%lld\n", datas[1].datetime); - printf("%s\n", datas[1].previsions.desc); - printf("%f\n", datas[1].previsions.min); - printf("%lld\n", datas[2].datetime); - printf("%s\n", datas[2].previsions.desc); - printf("%f\n", datas[2].previsions.min); - ESP_LOGE(TAG, "fin debug"); - */ - if (lvgl_port_lock(0)) - { - ESP_LOGE(TAG, "------------------------------------- Set des subjects J --------------------------------"); - //Prévisions des 3 prochains jours - lv_subject_set_pointer(&forecastD1Subj, &dailyDatas[0]); - lv_subject_set_pointer(&forecastD2Subj, &dailyDatas[1]); - lv_subject_set_pointer(&forecastD3Subj, &dailyDatas[2]); - - ESP_LOGE(TAG, "------------------------------------- Set des subjects H--------------------------------"); - //Prévisions des 3 prochains jours - ESP_LOGE(TAG,"Pointeur %lli",datas[0].datetime); - lv_subject_set_pointer(&forecastH1Subj, &datas[0]); - lv_subject_set_pointer(&forecastH2Subj, &datas[1]); - lv_subject_set_pointer(&forecastH3Subj, &datas[2]); - - lv_subject_set_int(&meteoStatus,0); - lvgl_port_unlock(); - //ESP_LOGE(TAG, "------------------------------------- Fin Set des subjects --------------------------------"); - } -} - -void mount_sd_card(){ - // Options for mounting the filesystem. - // If format_if_mount_failed is set to true, SD card will be partitioned and - // formatted in case when mounting fails. - esp_vfs_fat_sdmmc_mount_config_t mount_config = { - .format_if_mount_failed = false, - .max_files = 5, - .allocation_unit_size = 16 * 1024 - }; - sdmmc_card_t *card; - const char mount_point[] = MOUNT_POINT; - ESP_LOGI(TAG, "Initializing SD card"); - - ESP_LOGI(TAG, "Using SPI peripheral"); - - sdmmc_host_t host = SDSPI_HOST_DEFAULT(); - - spi_bus_config_t bus_cfg = { - .mosi_io_num = PIN_NUM_MOSI, - .miso_io_num = PIN_NUM_MISO, - .sclk_io_num = PIN_NUM_CLK, - .quadwp_io_num = -1, - .quadhd_io_num = -1, - .max_transfer_sz = 4000, - }; - esp_err_t ret = spi_bus_initialize(host.slot, &bus_cfg, SDSPI_DEFAULT_DMA); - if (ret != ESP_OK) { - ESP_LOGE(TAG, "Failed to initialize bus."); - return; - } - - sdspi_device_config_t slot_config = SDSPI_DEVICE_CONFIG_DEFAULT(); - slot_config.gpio_cs = PIN_NUM_CS; - slot_config.host_id = host.slot; - - ESP_LOGI(TAG, "Mounting filesystem"); - ret = esp_vfs_fat_sdspi_mount(mount_point, &host, &slot_config, &mount_config, &card); - - if (ret != ESP_OK) { - if (ret == ESP_FAIL) { - ESP_LOGE(TAG, "Failed to mount filesystem. " - "If you want the card to be formatted, set the CONFIG_EXAMPLE_FORMAT_IF_MOUNT_FAILED menuconfig option."); - } else { - ESP_LOGE(TAG, "Failed to initialize the card (%s). " - "Make sure SD card lines have pull-up resistors in place.", esp_err_to_name(ret)); - } - return; - } - ESP_LOGI(TAG, "Filesystem mounted"); - - // Card has been initialized, print its properties - sdmmc_card_print_info(stdout, card); - -} - -void app_main(void){ - printf("Minimum free heap size: %" PRIu32 " bytes\n", esp_get_minimum_free_heap_size()); - printf("Free heap size: %" PRIu32 " bytes\n", esp_get_free_heap_size()); - - printf("1- Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - - esp_log_level_set("wifi", ESP_LOG_ERROR); - - printf("2- Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - - mount_sd_card(); - - - esp_vfs_littlefs_conf_t conf = { - .base_path = "/littlefs", - .partition_label = "littlefs", - .format_if_mount_failed = true, - .dont_mount = false, - }; - - printf("3 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - /* LCD HW initialization */ - ESP_ERROR_CHECK(app_lcd_init()); - - printf("4 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - /* Touch initialization */ - ESP_ERROR_CHECK(app_touch_init()); - - printf("5 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - /* LVGL initialization */ - ESP_ERROR_CHECK(app_lvgl_init()); - - printf("6 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - - /* On affiche au plus tot l'ecran de démarrage */ - if(lvgl_port_lock(0)){ - //ESP_ERROR_CHECK(esp_lcd_panel_mirror(lcd_panel,true,true)); - app_main_display(); - lvgl_port_unlock(); - } - - - printf("7 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - // Initialize NVS - esp_err_t ret = nvs_flash_init(); - if (ret == ESP_ERR_NVS_NO_FREE_PAGES || ret == ESP_ERR_NVS_NEW_VERSION_FOUND) - { - ESP_ERROR_CHECK(nvs_flash_erase()); - ret = nvs_flash_init(); - } - ESP_ERROR_CHECK(ret); - - lv_subject_init_int(&meteoStatus,-1); - - printf("8 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - ESP_LOGI(TAG, "ESP_WIFI_MODE_STA"); - wifi_init_sta(); - printf("8b - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - mqtt_app_start(); - - printf("9 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - time_t now; - struct tm timeinfo; - time(&now); - localtime_r(&now, &timeinfo); - // Is time set? If not, tm_year will be (1970 - 1900). - if (timeinfo.tm_year < (2016 - 1900)) { - ESP_LOGI(TAG, "Time is not set yet. Connecting to WiFi and getting time over NTP."); - obtain_time(); - // update 'now' variable with current time - time(&now); - } - - char strftime_buf[64]; - - // Set timezone to Eastern Standard Time and print local time - setenv("TZ", "CET-1CEST,M3.5.0,M10.5.0/3", 1); - tzset(); - localtime_r(&now, &timeinfo); - strftime(strftime_buf, sizeof(strftime_buf), "%c", &timeinfo); - - printf("10. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - heap_caps_print_heap_info(MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT); - - - on_weather_data_retrieval(weather_data_retreived); - on_weather_data_retrieval_start(weather_data_retreived_start); - initialise_weather_data_retrieval(600000); - ESP_LOGW(TAG, "Weather data retrieval initialized"); - - printf("11. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - ESP_LOGW(TAG, "On telecharge l'image cuve"); - TaskHandle_t xHandle = NULL; - BaseType_t ret1 = xTaskCreate(&imgdwn, "imageDownload_task", 3 * 1024, NULL, 5, &xHandle); - if(ret1!=pdPASS ){ - ESP_LOGE(TAG, "Impossiblke de creer la tache %i", ret1); - } - - - - printf("12. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - /* Show LVGL objects */ - if(lvgl_port_lock(0)){ - draw_ihm(); - //lv_disp_set_rotation(lvgl_disp, LV_DISPLAY_ROTATION_180); - - lvgl_port_unlock(); - } - printf("13. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); - printf("Minimum free heap size: %" PRIu32 " bytes\n", esp_get_minimum_free_heap_size()); - printf("Free heap size: %" PRIu32 " bytes\n", esp_get_free_heap_size()); -LV_ASSERT_MEM_INTEGRITY(); - -lv_mem_monitor_t mon; -lv_mem_monitor(&mon); -printf("used: %6d (%3d %%), frag: %3d %%, biggest free: %6d\n", - (int)mon.total_size - mon.free_size, mon.used_pct, mon.frag_pct, - (int)mon.free_biggest_size); - - ESP_LOGI(TAG, "Initializing LittleFS"); - - esp_vfs_littlefs_conf_t conflfs = { - .base_path = "/littlefs", - .partition_label = "littlefs", - .format_if_mount_failed = true, - .dont_mount = false, - }; - - // Use settings defined above to initialize and mount LittleFS filesystem. - // Note: esp_vfs_littlefs_register is an all-in-one convenience function. - ret = esp_vfs_littlefs_register(&conflfs); - - if (ret != ESP_OK) - { - if (ret == ESP_FAIL) - { - ESP_LOGE(TAG, "Failed to mount or format filesystem"); - } - else if (ret == ESP_ERR_NOT_FOUND) - { - ESP_LOGE(TAG, "Failed to find LittleFS partition"); - } - else - { - ESP_LOGE(TAG, "Failed to initialize LittleFS (%s)", esp_err_to_name(ret)); - } - return; - } - - size_t total = 0, used = 0; - ret = esp_littlefs_info(conflfs.partition_label, &total, &used); - if (ret != ESP_OK) - { - ESP_LOGE(TAG, "Failed to get LittleFS partition information (%s)", esp_err_to_name(ret)); - } - else - { - ESP_LOGI(TAG, "Partition size: total: %d, used: %d", total, used); - } - - ESP_LOGI(TAG, "Reading file"); - FILE *f = fopen("/littlefs/p1j.png", "r"); - if (f == NULL) - { - ESP_LOGE(TAG, "Failed to open file for reading"); - return; - } - - char line[128]; - char *pos; - - fgets(line, sizeof(line), f); - fclose(f); - // strip newline - pos = strchr(line, '\n'); - if (pos) - { - *pos = '\0'; - } - ESP_LOGI(TAG, "Read from file: '%s'", line); - - -} - - - +#include "misc/lv_types.h" +#include "freertos/FreeRTOS.h" +#include "freertos/event_groups.h" +#include "esp_err.h" +#include "esp_log.h" +#include "esp_check.h" +#include "driver/i2c.h" +#include "esp_lcd_panel_io.h" +#include "esp_lcd_panel_ops.h" +#include "esp_lcd_panel_rgb.h" +#include "esp_lcd_touch_gt911.h" +#include "esp_lvgl_port.h" +#include "esp_event.h" +#include "nvs_flash.h" +#include +#include "esp_vfs_fat.h" +#include "sdmmc_cmd.h" +#include + +// OTA +#include "esp_ota_ops.h" +#include "esp_http_client.h" +#include "esp_https_ota.h" + + +// Includes personnels +#include "wifi_logger.h" +#include "obtain_time.h" +#include "fatfs.h" +#include "meteofrance.h" +#include "image_downloader.h" +#include "wifi.h" +#include "mqtt.h" + +#include "am2302_rmt.h" + +// GPIO assignment +#define AM2302_GPIO 19 + + +#include "esp_littlefs.h" + +#define MOUNT_POINT "/sdcard" +// Pin assignments can be set in menuconfig, see "SD SPI Example Configuration" menu. +// You can also change the pin assignments here by changing the following 4 lines. +#define PIN_NUM_MISO 13 +#define PIN_NUM_MOSI 11 +#define PIN_NUM_CLK 12 +#define PIN_NUM_CS 10 + +#include "main.h" +LV_FONT_DECLARE(montserrat_medium_12) +LV_FONT_DECLARE(montserrat_medium_18) +LV_FONT_DECLARE(montserrat_medium_24) + +/* LCD size */ +#define EXAMPLE_LCD_H_RES (800) +#define EXAMPLE_LCD_V_RES (480) + +/* LCD settings */ +#define EXAMPLE_LCD_LVGL_FULL_REFRESH (0) +#define EXAMPLE_LCD_LVGL_DIRECT_MODE (1) +#define EXAMPLE_LCD_LVGL_AVOID_TEAR (1) +#define EXAMPLE_LCD_RGB_BOUNCE_BUFFER_MODE (1) +#define EXAMPLE_LCD_DRAW_BUFF_DOUBLE (1) +#define EXAMPLE_LCD_DRAW_BUFF_HEIGHT (100) +#define EXAMPLE_LCD_RGB_BUFFER_NUMS (2) +#define EXAMPLE_LCD_RGB_BOUNCE_BUFFER_HEIGHT (10) + +/* LCD pins */ +#define EXAMPLE_LCD_GPIO_VSYNC (GPIO_NUM_41) +#define EXAMPLE_LCD_GPIO_HSYNC (GPIO_NUM_39) +#define EXAMPLE_LCD_GPIO_DE (GPIO_NUM_40) +#define EXAMPLE_LCD_GPIO_PCLK (GPIO_NUM_42) +#define EXAMPLE_LCD_GPIO_DISP (GPIO_NUM_NC) +#define EXAMPLE_LCD_GPIO_DATA0 (GPIO_NUM_8) +#define EXAMPLE_LCD_GPIO_DATA1 (GPIO_NUM_3) +#define EXAMPLE_LCD_GPIO_DATA2 (GPIO_NUM_46) +#define EXAMPLE_LCD_GPIO_DATA3 (GPIO_NUM_9) +#define EXAMPLE_LCD_GPIO_DATA4 (GPIO_NUM_1) +#define EXAMPLE_LCD_GPIO_DATA5 (GPIO_NUM_5) +#define EXAMPLE_LCD_GPIO_DATA6 (GPIO_NUM_6) +#define EXAMPLE_LCD_GPIO_DATA7 (GPIO_NUM_7) +#define EXAMPLE_LCD_GPIO_DATA8 (GPIO_NUM_15) +#define EXAMPLE_LCD_GPIO_DATA9 (GPIO_NUM_16) +#define EXAMPLE_LCD_GPIO_DATA10 (GPIO_NUM_4) +#define EXAMPLE_LCD_GPIO_DATA11 (GPIO_NUM_45) +#define EXAMPLE_LCD_GPIO_DATA12 (GPIO_NUM_48) +#define EXAMPLE_LCD_GPIO_DATA13 (GPIO_NUM_47) +#define EXAMPLE_LCD_GPIO_DATA14 (GPIO_NUM_21) +#define EXAMPLE_LCD_GPIO_DATA15 (GPIO_NUM_14) + +/* Touch settings */ +#define EXAMPLE_TOUCH_I2C_NUM (0) +#define EXAMPLE_TOUCH_I2C_CLK_HZ (400000) + +/* LCD touch pins */ +#define EXAMPLE_TOUCH_I2C_SCL (GPIO_NUM_18) +#define EXAMPLE_TOUCH_I2C_SDA (GPIO_NUM_17) + +#define EXAMPLE_LCD_PANEL_35HZ_RGB_TIMING() \ + { \ + .pclk_hz = 16 * 1000 * 1000, \ + .h_res = EXAMPLE_LCD_H_RES, \ + .v_res = EXAMPLE_LCD_V_RES, \ + .hsync_pulse_width = 4, \ + .hsync_back_porch = 8, \ + .hsync_front_porch = 8, \ + .vsync_pulse_width = 4, \ + .vsync_back_porch = 8, \ + .vsync_front_porch = 8, \ + .flags.pclk_active_neg = true, \ + .flags.hsync_idle_low = true, \ + } + +static const char *TAG = "domoTic"; + +extern char *upEvent; +extern char *downEvent; + +// LVGL image declare +LV_IMG_DECLARE(esp_logo) + +/* LCD IO and panel */ +static esp_lcd_panel_handle_t lcd_panel = NULL; +static esp_lcd_touch_handle_t touch_handle = NULL; + +/* LVGL display and touch */ +static lv_display_t *lvgl_disp = NULL; +static lv_indev_t *lvgl_touch_indev = NULL; + +lv_obj_t *chart; +lv_chart_series_t *ser1; + +static esp_err_t app_lcd_init(void) +{ + esp_err_t ret = ESP_OK; + + /* LCD initialization */ + ESP_LOGI(TAG, "Initialize RGB panel"); + esp_lcd_rgb_panel_config_t panel_conf = { + .clk_src = LCD_CLK_SRC_PLL160M, + .psram_trans_align = 64, + .data_width = 16, + .bits_per_pixel = 16, + .de_gpio_num = EXAMPLE_LCD_GPIO_DE, + .pclk_gpio_num = EXAMPLE_LCD_GPIO_PCLK, + .vsync_gpio_num = EXAMPLE_LCD_GPIO_VSYNC, + .hsync_gpio_num = EXAMPLE_LCD_GPIO_HSYNC, + .disp_gpio_num = EXAMPLE_LCD_GPIO_DISP, + .data_gpio_nums = { + EXAMPLE_LCD_GPIO_DATA0, + EXAMPLE_LCD_GPIO_DATA1, + EXAMPLE_LCD_GPIO_DATA2, + EXAMPLE_LCD_GPIO_DATA3, + EXAMPLE_LCD_GPIO_DATA4, + EXAMPLE_LCD_GPIO_DATA5, + EXAMPLE_LCD_GPIO_DATA6, + EXAMPLE_LCD_GPIO_DATA7, + EXAMPLE_LCD_GPIO_DATA8, + EXAMPLE_LCD_GPIO_DATA9, + EXAMPLE_LCD_GPIO_DATA10, + EXAMPLE_LCD_GPIO_DATA11, + EXAMPLE_LCD_GPIO_DATA12, + EXAMPLE_LCD_GPIO_DATA13, + EXAMPLE_LCD_GPIO_DATA14, + EXAMPLE_LCD_GPIO_DATA15, + }, + .timings = EXAMPLE_LCD_PANEL_35HZ_RGB_TIMING(), + .flags.fb_in_psram = 1, + .num_fbs = EXAMPLE_LCD_RGB_BUFFER_NUMS, +#if EXAMPLE_LCD_RGB_BOUNCE_BUFFER_MODE + .bounce_buffer_size_px = EXAMPLE_LCD_H_RES * EXAMPLE_LCD_RGB_BOUNCE_BUFFER_HEIGHT, +#endif + }; + ESP_GOTO_ON_ERROR(esp_lcd_new_rgb_panel(&panel_conf, &lcd_panel), err, TAG, "RGB init failed"); + ESP_GOTO_ON_ERROR(esp_lcd_panel_init(lcd_panel), err, TAG, "LCD init failed"); + + return ret; + +err: + if (lcd_panel) + { + esp_lcd_panel_del(lcd_panel); + } + return ret; +} + +static esp_err_t app_touch_init(void) +{ + /* Initilize I2C */ + const i2c_config_t i2c_conf = { + .mode = I2C_MODE_MASTER, + .sda_io_num = EXAMPLE_TOUCH_I2C_SDA, + .sda_pullup_en = GPIO_PULLUP_DISABLE, + .scl_io_num = EXAMPLE_TOUCH_I2C_SCL, + .scl_pullup_en = GPIO_PULLUP_DISABLE, + .master.clk_speed = EXAMPLE_TOUCH_I2C_CLK_HZ}; + ESP_RETURN_ON_ERROR(i2c_param_config(EXAMPLE_TOUCH_I2C_NUM, &i2c_conf), TAG, "I2C configuration failed"); + ESP_RETURN_ON_ERROR(i2c_driver_install(EXAMPLE_TOUCH_I2C_NUM, i2c_conf.mode, 0, 0, 0), TAG, "I2C initialization failed"); + + /* Initialize touch HW */ + const esp_lcd_touch_config_t tp_cfg = { + .x_max = EXAMPLE_LCD_H_RES, + .y_max = EXAMPLE_LCD_V_RES, + .rst_gpio_num = GPIO_NUM_NC, + .int_gpio_num = GPIO_NUM_NC, + .levels = { + .reset = 0, + .interrupt = 0, + }, + .flags = { + .swap_xy = 0, + .mirror_x = 0, + .mirror_y = 0, + }, + }; + esp_lcd_panel_io_handle_t tp_io_handle = NULL; + const esp_lcd_panel_io_i2c_config_t tp_io_config = ESP_LCD_TOUCH_IO_I2C_GT911_CONFIG(); + ESP_RETURN_ON_ERROR(esp_lcd_new_panel_io_i2c((esp_lcd_i2c_bus_handle_t)EXAMPLE_TOUCH_I2C_NUM, &tp_io_config, &tp_io_handle), TAG, ""); + return esp_lcd_touch_new_i2c_gt911(tp_io_handle, &tp_cfg, &touch_handle); +} + +static esp_err_t app_lvgl_init(void) +{ + /* Initialize LVGL */ + const lvgl_port_cfg_t lvgl_cfg = { + .task_priority = 4, /* LVGL task priority */ + .task_stack = 12288, // 6144, /* LVGL task stack size */ + .task_affinity = -1, /* LVGL task pinned to core (-1 is no affinity) */ + .task_max_sleep_ms = 500, /* Maximum sleep in LVGL task */ + .timer_period_ms = 5 /* LVGL timer tick period in ms */ + }; + ESP_RETURN_ON_ERROR(lvgl_port_init(&lvgl_cfg), TAG, "LVGL port initialization failed"); + + uint32_t buff_size = EXAMPLE_LCD_H_RES * EXAMPLE_LCD_DRAW_BUFF_HEIGHT; +#if EXAMPLE_LCD_LVGL_FULL_REFRESH || EXAMPLE_LCD_LVGL_DIRECT_MODE + buff_size = EXAMPLE_LCD_H_RES * EXAMPLE_LCD_V_RES; +#endif + + /* Add LCD screen */ + ESP_LOGD(TAG, "Add LCD screen"); + const lvgl_port_display_cfg_t disp_cfg = { + .panel_handle = lcd_panel, + .buffer_size = buff_size, + .double_buffer = EXAMPLE_LCD_DRAW_BUFF_DOUBLE, + .hres = EXAMPLE_LCD_H_RES, + .vres = EXAMPLE_LCD_V_RES, + .monochrome = false, +#if LVGL_VERSION_MAJOR >= 9 + .color_format = LV_COLOR_FORMAT_RGB565, +#endif + .rotation = { + .swap_xy = false, + .mirror_x = false, + .mirror_y = false, + }, + .flags = { + .buff_dma = false, + .buff_spiram = false, +#if EXAMPLE_LCD_LVGL_FULL_REFRESH + .full_refresh = true, +#elif EXAMPLE_LCD_LVGL_DIRECT_MODE + .direct_mode = true, +#endif +#if LVGL_VERSION_MAJOR >= 9 + .swap_bytes = false, +#endif + }}; + const lvgl_port_display_rgb_cfg_t rgb_cfg = { + .flags = { +#if EXAMPLE_LCD_RGB_BOUNCE_BUFFER_MODE + .bb_mode = true, +#else + .bb_mode = false, +#endif +#if EXAMPLE_LCD_LVGL_AVOID_TEAR + .avoid_tearing = true, +#else + .avoid_tearing = false, +#endif + }}; + lvgl_disp = lvgl_port_add_disp_rgb(&disp_cfg, &rgb_cfg); + + /* Add touch input (for selected screen) */ + const lvgl_port_touch_cfg_t touch_cfg = { + .disp = lvgl_disp, + .handle = touch_handle, + }; + lvgl_touch_indev = lvgl_port_add_touch(&touch_cfg); + + return ESP_OK; +} + +static void _app_button_cb(lv_event_t *e) +{ + if (lvgl_port_lock(0)) + { + lv_disp_rotation_t rotation = lv_disp_get_rotation(lvgl_disp); + rotation++; + if (rotation > LV_DISPLAY_ROTATION_270) + { + rotation = LV_DISPLAY_ROTATION_0; + } + + /* LCD HW rotation */ + lv_disp_set_rotation(lvgl_disp, rotation); + lvgl_port_unlock(); + } +} + +lv_subject_t meteoStatus; +lv_subject_t dateHeureSubj; +char dateHeureStr[30]; + +static lv_style_t no_padding; +static lv_style_t style_font_18; +static lv_style_t style_font_24; + +struct lv_observer_t +{ + lv_subject_t *subject; /**< The observed value */ + lv_observer_cb_t cb; /**< Callback that should be called when the value changes*/ + void *target; /**< A target for the observer, e.g. a widget or style*/ + void *user_data; /**< Additional parameter supplied when subscribing*/ + uint32_t auto_free_user_data : 1; /**< Automatically free user data when the observer is removed */ + uint32_t notified : 1; /**< Mark if this observer was already notified*/ + uint32_t for_obj : 1; /**< `target` is an `lv_obj_t *`*/ +}; + +static void meteo_obs_cb(lv_observer_t *observer, lv_subject_t *subject) +{ + ESP_LOGV("MeteoFrance", "On passe dans le callback de chgt de statut meteo; %li", lv_subject_get_int(subject)); + if (lvgl_port_lock(0)) + { + lv_obj_t *meteoSt = observer->target; + switch (lv_subject_get_int(subject)) + { + case 0: + lv_obj_set_style_text_color(meteoSt, lv_color_make(0x00, 0xff, 0xff), 0); + break; + case 1: + lv_obj_set_style_text_color(meteoSt, lv_color_make(0xff, 0x00, 0x00), 0); + break; + } + lvgl_port_unlock(); + } +} + +static void app_main_display(void) +{ + + lv_subject_init_string(&dateHeureSubj, dateHeureStr, NULL, 64, "--"); + + lv_style_init(&no_padding); + lv_style_set_pad_all(&no_padding, 0); + + lv_style_init(&style_font_18); + lv_style_set_text_font(&style_font_18, &montserrat_medium_18); + + lv_obj_t *cont_status = lv_obj_create(lv_layer_top()); + lv_obj_add_style(cont_status, &no_padding, 0); + lv_obj_align(cont_status, LV_ALIGN_TOP_RIGHT, 0, 0); + lv_obj_set_flex_flow(cont_status, LV_FLEX_FLOW_ROW); + lv_obj_set_height(cont_status, LV_SIZE_CONTENT); + lv_obj_set_width(cont_status, LV_SIZE_CONTENT); + + lv_obj_t *jour = lv_label_create(cont_status); + lv_obj_add_style(jour, &style_font_18, 0); + lv_obj_set_width(jour, LV_SIZE_CONTENT); + lv_label_bind_text(jour, &dateHeureSubj, NULL); + + lv_obj_refr_size(cont_status); + // lv_obj_align(jour, LV_ALIGN_CENTER,0,0); + + lv_obj_t *meteoR = lv_label_create(cont_status); + lv_obj_add_style(meteoR, &style_font_18, 0); + lv_label_set_text(meteoR, "\xEF\x83\x82"); + lv_obj_set_style_text_color(meteoR, lv_color_make(0x00, 0xff, 0xff), 0); + lv_subject_add_observer_obj(&meteoStatus, meteo_obs_cb, meteoR, NULL); + + // lv_label_bind_text(meteoR, &meteoStatus, "Meteo %d"); + + lv_obj_t *wifi = lv_image_create(cont_status); + // lv_obj_set_style_bg_color(wifi, lv_palette_darken(LV_PALETTE_GREY, 3), 0); + // lv_obj_set_style_border_width(wifi,1,0); + // lv_obj_set_style_border_color(wifi,lv_palette_darken(LV_PALETTE_GREY, 3),0); + // lv_label_set_text(wifi,"Wifi Ok"); + // lv_label_bind_text(wifi, &wifiStatus, "Wifi %d"); + + lv_image_create(cont_status); + // lv_label_set_text(mqtt,"Mqtt Ok"); + // lv_label_bind_text(mqtt, &mqttStatus, "Mqtt %d"); + + lv_obj_t *scr = lv_scr_act(); + + /* Your LVGL objects code here .... */ + + /* Create image */ + lv_obj_t *img_logo = lv_img_create(scr); + lv_img_set_src(img_logo, &esp_logo); + lv_obj_align(img_logo, LV_ALIGN_TOP_MID, 0, 20); + /* Label */ + lv_obj_t *label = lv_label_create(scr); + lv_obj_set_width(label, EXAMPLE_LCD_H_RES); + lv_obj_set_style_text_align(label, LV_TEXT_ALIGN_CENTER, 0); +#if LVGL_VERSION_MAJOR == 8 + lv_label_set_recolor(label, true); + lv_label_set_text(label, "#FF0000 " LV_SYMBOL_BELL " Hello world Espressif and LVGL " LV_SYMBOL_BELL "#\n#FF9400 " LV_SYMBOL_WARNING " For simplier initialization, use BSP " LV_SYMBOL_WARNING " #"); +#else + lv_label_set_text(label, LV_SYMBOL_BELL "Bienvenue sur DomoTIC !" LV_SYMBOL_BELL); +#endif + lv_obj_align(label, LV_ALIGN_CENTER, 0, 20); +} + +char tempExtStr[6]; +char tempIntStr[6]; +char hauteurCuveStr[9]; +char hauteurCuveEvolStr[9]; +lv_subject_t tempIntSubj; +lv_subject_t tempExtSubj; +lv_subject_t hauteurCuveSubj; +lv_subject_t hauteurCuveEvolSubj; +lv_subject_t forecastD1Subj; +lv_subject_t forecastD2Subj; +lv_subject_t forecastD3Subj; +lv_subject_t *tmpSubj[3] = {&forecastD1Subj, &forecastD2Subj, &forecastD3Subj}; +lv_subject_t forecastH1Subj; +lv_subject_t forecastH2Subj; +lv_subject_t forecastH3Subj; +lv_subject_t *tmpHSubj[3] = {&forecastH1Subj, &forecastH2Subj, &forecastH3Subj}; + +extern esp_mqtt_client_handle_t client; + +static void event_handler(lv_event_t *e) +{ + lv_event_code_t code = lv_event_get_code(e); + // lv_obj_t *obj = (lv_obj_t *)lv_event_get_target(e); + char *evtData = (char *)lv_event_get_user_data(e); + + switch (code) + { + case LV_EVENT_PRESSED: + // LV_LOG_USER("%s was pressed\n", evtData); + break; + case LV_EVENT_CLICKED: + ESP_LOGI(TAG, "%s was clicked\n", evtData); + esp_mqtt_client_publish(client, "volets", evtData, 0, 0, 0); + break; + case LV_EVENT_LONG_PRESSED: + LV_LOG_USER("%s was long pressed\n", evtData); + break; + case LV_EVENT_LONG_PRESSED_REPEAT: + LV_LOG_USER("%s was long press repeat\n", evtData); + break; + default: + break; + } +} +LV_IMAGE_DECLARE(plan_rdc); +LV_IMAGE_DECLARE(plan_etage); +/* +LV_IMAGE_DECLARE(p1j); +LV_IMAGE_DECLARE(p2j); +LV_IMAGE_DECLARE(p3j); +LV_IMAGE_DECLARE(p4j); +LV_IMAGE_DECLARE(p5bisj); +LV_IMAGE_DECLARE(p12j); +LV_IMAGE_DECLARE(p12bisj); +LV_IMAGE_DECLARE(p13j); +LV_IMAGE_DECLARE(p13bisj); +LV_IMAGE_DECLARE(p14j); +LV_IMAGE_DECLARE(p24j); +LV_IMAGE_DECLARE(p25j); +LV_IMAGE_DECLARE(p26j); +LV_IMAGE_DECLARE(p27j); +LV_IMAGE_DECLARE(p28j); +LV_IMAGE_DECLARE(p29j); +*/ + +static lv_style_t style_container; +static lv_style_t style_font_12; + +// Callback pour mettre à jour une météo journaliere +// On pointe sur un tableau de meteodailyforecast_data +static void weatherdata_obs_cb(lv_observer_t *observer, lv_subject_t *subject) +{ + + ESP_LOGE(TAG, "CB meteo jour declenché"); + // Retrieve weatherdata + const struct meteodailyforecast_data *data = subject->value.pointer; + // printffd(data); + // char buff[40] = {}; + // sprintf(buff,"%s %.1f %.1f", data->previsions.desc, data->previsions.min, data->previsions.max); + + lv_obj_t *parent = (lv_obj_t *)(observer->target); + lv_obj_t *datefld = lv_obj_get_child(parent, 0); + lv_obj_t *desc_icon = lv_obj_get_child(parent, 1); + lv_obj_t *temps = lv_obj_get_child(parent, 2); + showMeteoIcon(data->previsions.icon, desc_icon, 0); + char buffer[80]; + dtToString(data->datetime, buffer); + + lv_label_set_text(datefld, buffer); + lv_label_set_text(lv_obj_get_child(desc_icon, 1), data->previsions.desc); + lv_label_set_text_fmt(lv_obj_get_child(temps, 0), "%.1f°C", data->previsions.max); + lv_label_set_text_fmt(lv_obj_get_child(temps, 1), "%.1f°C", data->previsions.min); +} + +// Callback pour mettre à jour une météo horaire +// On pointe sur un tableau de meteoforecast_data +static void weatherdataH_obs_cb(lv_observer_t *observer, lv_subject_t *subject) +{ + ESP_LOGV("MeteoFrance", "CB meteo horaire declenché"); + // Retrieve weatherdata + const struct meteoforecast_data *data = subject->value.pointer; + // printffd(data); + // char buff[40] = {}; + // sprintf(buff,"%s %.1f %.1f", data->previsions.desc, data->previsions.min, data->previsions.max); + + lv_obj_t *parent = (lv_obj_t *)(observer->target); + lv_obj_t *datefld = lv_obj_get_child(parent, 0); + lv_obj_t *temp_desc_icon = lv_obj_get_child(parent, 1); + showMeteoIcon(data->previsions.icon, temp_desc_icon, 1); + + char buffer[80]; + dtHToString(data->datetime, buffer); + + lv_label_set_text(datefld, buffer); + lv_label_set_text(lv_obj_get_child(temp_desc_icon, 2), data->previsions.desc); + lv_label_set_text_fmt(lv_obj_get_child(temp_desc_icon, 0), "%.1f°C", data->previsions.value); +} + +void showMeteoIcon(const char *icon, lv_obj_t *desc_icon, int childNr) +{ + lv_obj_t *img = lv_obj_get_child(desc_icon, childNr); + char *str1 = "A:/littlefs/"; + char *result = malloc(strlen(str1) + strlen(icon) + 6); + sprintf(result, "%s%s.png", str1, icon); + lv_image_set_src(img, result); + /* + if (strcmp(icon, "p1j") == 0) + { + lv_image_set_src(img, &p1j); + } + else if (strcmp(icon, "p2j") == 0) + { + lv_image_set_src(img, &p2j); + } + else if (strcmp(icon, "p3j") == 0) + { + lv_image_set_src(img, &p3j); + } + else if (strcmp(icon, "p4j") == 0) + { + lv_image_set_src(img, &p4j); + } + else if (strcmp(icon, "p5bisj") == 0) + { + lv_image_set_src(img, &p5bisj); + } + else if (strcmp(icon, "p12j") == 0) + { + lv_image_set_src(img, &p12j); + } + else if (strcmp(icon, "p12bisj") == 0) + { + lv_image_set_src(img, &p12bisj); + } + else if (strcmp(icon, "p13j") == 0) + { + lv_image_set_src(img, &p13j); + } + else if (strcmp(icon, "p13bisj") == 0) + { + lv_image_set_src(img, &p13bisj); + } + else if (strcmp(icon, "p14j") == 0) + { + lv_image_set_src(img, &p14j); + } + else if (strcmp(icon, "p24j") == 0) + { + lv_image_set_src(img, &p24j); + } + else if (strcmp(icon, "p25j") == 0) + { + lv_image_set_src(img, &p25j); + } + else if (strcmp(icon, "p26j") == 0) + { + lv_image_set_src(img, &p26j); + } + else if (strcmp(icon, "p27j") == 0) + { + lv_image_set_src(img, &p27j); + } + else if (strcmp(icon, "p28j") == 0) + { + lv_image_set_src(img, &p28j); + } + else if (strcmp(icon, "p29j") == 0) + { + lv_image_set_src(img, &p29j); + } + else + { + ESP_LOGE(TAG, "Image %s non connue", icon); + } + */ +} +/* ------------------------------------------------------------ */ +/* Fragment meteo journaliere (date,icone, min et max) */ +/* ------------------------------------------------------------ */ + +// Structure meteo journaliere +struct weatherDay_fragment_t +{ + /* IMPORTANT: don't miss this part */ + lv_fragment_t base; + /* States, object references and data fields for this fragment */ + int dayNr; + bool showTitle; + const char *title; + float minTemp; + float maxTemp; +}; + +// Constructeur meteo journaliere +static void weatherDay_fragment_ctor(lv_fragment_t *self, void *args) +{ + int dayNo = ((int *)args)[0]; + bool showDate = ((int *)args)[1]; + ((struct weatherDay_fragment_t *)self)->dayNr = dayNo; + ((struct weatherDay_fragment_t *)self)->showTitle = showDate; + ESP_LOGI(TAG, "Fragment initialisé avec le jour n°%d - Afficher la date %d", dayNo, showDate); +} + +// Ce fragment affiche une prévision journaliere (date,icone, min et max) +static lv_obj_t *weatherDay_fragment_create_obj(lv_fragment_t *self, lv_obj_t *parent) +{ + + lv_obj_t *sup = lv_obj_create(parent); + + lv_obj_t *title = lv_label_create(sup); + lv_label_set_text(title, "--"); + + lv_obj_set_flex_flow(sup, LV_FLEX_FLOW_ROW); + lv_obj_add_style(sup, &style_container, 0); + lv_obj_set_size(sup, LV_SIZE_CONTENT, LV_SIZE_CONTENT); + + lv_obj_t *container = lv_obj_create(sup); + lv_obj_set_flex_flow(container, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(container, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); + lv_obj_add_style(container, &no_padding, 0); + lv_obj_set_width(container, 150); + lv_obj_set_height(container, 80); + + lv_obj_t *img1 = lv_image_create(container); + lv_obj_add_style(img1, &no_padding, 0); + lv_obj_set_style_bg_color(img1, lv_palette_lighten(LV_PALETTE_BLUE_GREY, 4), 0); + lv_image_set_inner_align(img1, LV_IMAGE_ALIGN_TOP_LEFT); + lv_image_set_offset_y(img1, -8); + lv_image_set_offset_x(img1, -5); + lv_obj_set_size(img1, 40, 32); + lv_image_set_src(img1, LV_SYMBOL_DUMMY); + // lv_obj_set_style_border_width(img1,2,0); + // lv_obj_set_style_border_color(img1, lv_palette_main(LV_PALETTE_BLUE_GREY), 0); + lv_obj_align(img1, LV_ALIGN_CENTER, 0, 0); + + lv_obj_t *desc = lv_label_create(container); + lv_label_set_text(desc, "--"); + lv_obj_add_style(desc, &style_font_12, 0); + + lv_obj_t *container2 = lv_obj_create(sup); + lv_obj_set_width(container2, LV_SIZE_CONTENT); + lv_obj_set_height(container2, 80); + lv_obj_add_style(container2, &no_padding, 0); + lv_obj_set_style_pad_top(container2, 5, 0); + lv_obj_set_style_pad_bottom(container2, 5, 0); + lv_obj_set_flex_flow(container2, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(container2, LV_FLEX_ALIGN_SPACE_BETWEEN, LV_FLEX_ALIGN_START, LV_FLEX_ALIGN_START); + + static lv_style_t tempStyle; + lv_style_init(&tempStyle); + // lv_style_set_text_font(&tempStyle,¬omedium16); + + lv_obj_t *max = lv_label_create(container2); + lv_label_set_text(max, "--"); + lv_obj_add_style(max, &tempStyle, 0); + lv_obj_add_style(max, &style_font_18, 0); + lv_obj_set_style_text_color(max, lv_color_hex(0xFF0000), 0); + lv_obj_add_style(max, &style_font_18, 0); + + lv_obj_t *min = lv_label_create(container2); + lv_label_set_text(min, "--"); + lv_obj_add_style(min, &tempStyle, 0); + lv_obj_add_style(min, &style_font_18, 0); + lv_obj_set_style_text_color(min, lv_color_hex(0x3000FF), 0); + lv_obj_add_style(min, &style_font_18, 0); + + // On positionne un observer sur le subjet correspondant au jour du widget + lv_subject_add_observer_obj(tmpSubj[((struct weatherDay_fragment_t *)self)->dayNr], weatherdata_obs_cb, sup, NULL); + return container; +} + +// Fragment meteo journaliere +const lv_fragment_class_t meteoFragment = { + /* Initialize something needed */ + .constructor_cb = weatherDay_fragment_ctor, + /* Create view objects */ + .create_obj_cb = weatherDay_fragment_create_obj, + /* IMPORTANT: size of your fragment struct */ + .instance_size = sizeof(struct weatherDay_fragment_t), +}; + +/* ------------------------------------------------------------ */ +/* Fragment meteo horaire ("heure",icone, temp) */ +/* ------------------------------------------------------------ */ + +// Structure meteo horaire +struct weatherH_fragment_t +{ + /* IMPORTANT: don't miss this part */ + lv_fragment_t base; + /* States, object references and data fields for this fragment */ + int horaireNr; + bool showTitle; + const char *horaire; + float temp; +}; + +// Constructeur meteo horaire +static void weatherH_fragment_ctor(lv_fragment_t *self, void *args) +{ + // Represente le n° (index dans le tableau) a afficher + int horaireNr = ((int *)args)[0]; + bool showDate = ((int *)args)[1]; + ((struct weatherH_fragment_t *)self)->horaireNr = horaireNr; + ((struct weatherH_fragment_t *)self)->showTitle = showDate; + ESP_LOGI(TAG, "Fragment initialisé avec l'horaire %d", horaireNr); +} + +// Ce fragment affiche une prévision horaire (date,icone, temp moyenne) +static lv_obj_t *weatherH_fragment_create_obj(lv_fragment_t *self, lv_obj_t *parent) +{ + + lv_obj_t *sup = lv_obj_create(parent); + + lv_obj_t *title = lv_label_create(sup); + lv_label_set_text(title, "--"); + + lv_obj_set_flex_flow(sup, LV_FLEX_FLOW_ROW); + lv_obj_add_style(sup, &style_container, 0); + lv_obj_set_size(sup, LV_SIZE_CONTENT, LV_SIZE_CONTENT); + + lv_obj_t *container = lv_obj_create(sup); + lv_obj_set_flex_flow(container, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(container, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); + lv_obj_add_style(container, &no_padding, 0); + lv_obj_set_width(container, 150); + lv_obj_set_height(container, LV_SIZE_CONTENT); + + static lv_style_t tempStyle; + lv_style_init(&tempStyle); + // lv_style_set_text_font(&tempStyle,¬omedium16); + + lv_obj_t *temp = lv_label_create(container); + lv_label_set_text(temp, "--"); + lv_obj_add_style(temp, &tempStyle, 0); + lv_obj_add_style(temp, &style_font_18, 0); + // lv_obj_set_style_text_color(temp,lv_color_hex(0xFF0000),0); + lv_obj_add_style(temp, &style_font_18, 0); + + lv_obj_t *img1 = lv_image_create(container); + lv_obj_add_style(img1, &no_padding, 0); + lv_obj_set_style_bg_color(img1, lv_palette_lighten(LV_PALETTE_BLUE_GREY, 4), 0); + lv_image_set_inner_align(img1, LV_IMAGE_ALIGN_TOP_LEFT); + lv_image_set_offset_y(img1, -8); + lv_image_set_offset_x(img1, -5); + lv_obj_set_size(img1, 40, 32); + lv_image_set_src(img1, LV_SYMBOL_DUMMY); + // lv_obj_set_style_border_width(img1,2,0); + // lv_obj_set_style_border_color(img1, lv_palette_main(LV_PALETTE_BLUE_GREY), 0); + lv_obj_align(img1, LV_ALIGN_CENTER, 0, 0); + + lv_obj_t *desc = lv_label_create(container); + lv_label_set_text(desc, "--"); + lv_obj_add_style(desc, &style_font_12, 0); + + // On positionne un observer sur le subjet correspondant a l'horaire du widget + ESP_LOGE(TAG, "on positionne obs sur horaire %d", ((struct weatherH_fragment_t *)self)->horaireNr); + lv_subject_add_observer_obj(tmpHSubj[((struct weatherH_fragment_t *)self)->horaireNr], weatherdataH_obs_cb, sup, NULL); + return container; +} + +// Fragment meteo horaire +const lv_fragment_class_t meteoHFragment = { + /* Initialize something needed */ + .constructor_cb = weatherH_fragment_ctor, + /* Create view objects */ + .create_obj_cb = weatherH_fragment_create_obj, + /* IMPORTANT: size of your fragment struct */ + .instance_size = sizeof(struct weatherH_fragment_t), +}; + +/* -------------------------------------------------------------- */ +/* Fragment 3 meteo "jour" (aujourd'hui, demain, apres demain) */ +/* -------------------------------------------------------------- */ +struct meteodailyforecast_fragment_t +{ + /* IMPORTANT: don't miss this part */ + lv_fragment_t base; + /* States, object references and data fields for this fragment */ + const char *title; + bool showDate; +}; + +static void meteodailyforecast_fragment_ctor(lv_fragment_t *self, void *args) +{ + struct meteodailyforecast_fragment_t *myself = ((struct meteodailyforecast_fragment_t *)self); + myself->showDate = args; +} + +static lv_obj_t *meteodailyforecast_fragment_create_obj(lv_fragment_t *self, lv_obj_t *parent) +{ + + lv_fragment_manager_t *manager = lv_fragment_manager_create(NULL); + + int args[2] = {0, ((struct meteodailyforecast_fragment_t *)self)->showDate}; + lv_fragment_t *fragment = lv_fragment_create(&meteoFragment, args); + lv_fragment_manager_add(manager, fragment, &parent); + + args[0] = 1; + fragment = lv_fragment_create(&meteoFragment, args); + lv_fragment_manager_add(manager, fragment, &parent); + + args[0] = 2; + fragment = lv_fragment_create(&meteoFragment, args); + lv_fragment_manager_add(manager, fragment, &parent); + + return parent; +} + +const lv_fragment_class_t meteodailyforecast_cls = { + /* Initialize something needed */ + .constructor_cb = meteodailyforecast_fragment_ctor, + /* Create view objects */ + .create_obj_cb = meteodailyforecast_fragment_create_obj, + /* IMPORTANT: size of your fragment struct */ + .instance_size = sizeof(struct meteodailyforecast_fragment_t), +}; +/* -------------------------------------------------------------------------------- */ +/* Fragment 3 meteo "horaire" - matin/midi/soir (icone, temp moyenne) */ +/* -------------------------------------------------------------------------------- */ + +struct meteoforecast_fragment_t +{ + /* IMPORTANT: don't miss this part */ + lv_fragment_t base; + /* States, object references and data fields for this fragment */ + const char *title; + bool showDate; +}; + +static void meteoforecast_fragment_ctor(lv_fragment_t *self, void *args) +{ + struct meteoforecast_fragment_t *myself = ((struct meteoforecast_fragment_t *)self); + myself->showDate = args; +} + +static lv_obj_t *meteoforecast_fragment_create_obj(lv_fragment_t *self, lv_obj_t *parent) +{ + + lv_fragment_manager_t *manager = lv_fragment_manager_create(NULL); + + // On affiche 3 fragment meteo. 1 pour chaque "horaire" + int args[2] = {0, ((struct meteoforecast_fragment_t *)self)->showDate}; + lv_fragment_t *fragment = lv_fragment_create(&meteoHFragment, args); + lv_fragment_manager_add(manager, fragment, &parent); + + args[0] = 1; + fragment = lv_fragment_create(&meteoHFragment, args); + lv_fragment_manager_add(manager, fragment, &parent); + + args[0] = 2; + fragment = lv_fragment_create(&meteoHFragment, args); + lv_fragment_manager_add(manager, fragment, &parent); + + return parent; +} + +const lv_fragment_class_t meteoforecast_cls = { + /* Initialize something needed */ + .constructor_cb = meteoforecast_fragment_ctor, + /* Create view objects */ + .create_obj_cb = meteoforecast_fragment_create_obj, + /* IMPORTANT: size of your fragment struct */ + .instance_size = sizeof(struct meteoforecast_fragment_t), +}; + +struct lv_event_t +{ + void *current_target; + void *original_target; + lv_event_code_t code; + void *user_data; + void *param; + lv_event_t *prev; + uint8_t deleted : 1; + uint8_t stop_processing : 1; + uint8_t stop_bubbling : 1; +}; + +lv_obj_t *tab0; +lv_obj_t *tabVolets; +lv_obj_t *tabMeteo; +lv_obj_t *tabCuve; +lv_obj_t *tabSettings; +uint32_t oldTab; +lv_fragment_manager_t *manager2; +lv_fragment_t *fragment2; + +static void tabChgEvt(lv_event_t *event) +{ + + uint32_t tabNr = lv_tabview_get_tab_active(event->user_data); + switch (oldTab) + { + case 1: + lv_obj_clean(tabVolets); + break; + case 2: + // lv_fragment_delete_obj(fragment2);; + // lv_fragment_manager_delete(manager2); + // lv_obj_clean(tab3); + break; + case 3: + lv_obj_clean(tabCuve); + break; + + default: + break; + } + + oldTab = tabNr; + + printf("Tab change %lu\n", tabNr); + switch (tabNr) + { + case 1: + draw_tabVolets(); + break; + case 2: // Onglet Météo + draw_tabMeteo(); + break; + + case 3: // Onglet Cuve + draw_tabCuve(); + break; + + case 4: // Onglet Settings + draw_tabSettings(); + break; + + default: + break; + } +} + +void btnRestart_cb(lv_event_t * e){ + lv_event_code_t code = lv_event_get_code(e); + + if(code == LV_EVENT_CLICKED) { + esp_restart(); + } + +} + +static void log_event_handler(lv_event_t * e) +{ + lv_event_code_t code = lv_event_get_code(e); + lv_obj_t * obj = lv_event_get_target(e); + if(code == LV_EVENT_VALUE_CHANGED) { + LV_UNUSED(obj); + char *tag=lv_event_get_user_data(e); + if(lv_obj_has_state(obj, LV_STATE_CHECKED)){ + esp_log_level_set(tag,ESP_LOG_DEBUG); + }else{ + esp_log_level_set(tag,ESP_LOG_INFO); + } + LV_LOG_USER("State for %s: %s\n", tag, lv_obj_has_state(obj, LV_STATE_CHECKED) ? "On" : "Off"); + } +} + +static lv_style_t style_lbvValue; +static lv_style_t style_btn; + +void draw_tabSettings() +{ + lv_obj_t *btnGrp = lv_obj_create(tabSettings); + lv_obj_set_height(btnGrp, 400); + lv_obj_set_flex_flow(btnGrp, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(btnGrp, LV_FLEX_ALIGN_END, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); + + lv_obj_align(btnGrp,LV_ALIGN_BOTTOM_MID,0,0); + lv_obj_t *btnRestart = lv_button_create(btnGrp); + lv_obj_t *lblRestart = lv_label_create(btnRestart); + lv_label_set_text(lblRestart,"Restart"); + lv_obj_add_event_cb(btnRestart, btnRestart_cb, LV_EVENT_CLICKED, NULL); + + lv_label_set_text(lv_label_create(btnGrp),"Meteo Debug"); + lv_obj_t *sw = lv_switch_create(btnGrp); + lv_obj_add_state(sw, LV_STATE_DEFAULT); + lv_obj_add_event_cb(sw, log_event_handler, LV_EVENT_ALL, "MeteoFrance"); + + lv_label_set_text(lv_label_create(btnGrp),"Cuve"); + sw = lv_switch_create(btnGrp); + lv_obj_add_state(sw, LV_STATE_DEFAULT); + lv_obj_add_event_cb(sw, log_event_handler, LV_EVENT_ALL, "ImgDwn"); + + lv_label_set_text(lv_label_create(btnGrp),"MQTT"); + sw = lv_switch_create(btnGrp); + lv_obj_add_state(sw, LV_STATE_DEFAULT); + lv_obj_add_event_cb(sw, log_event_handler, LV_EVENT_ALL, "domo_mqtt"); + + +} + +lv_obj_t *lblTempInt2; + +void draw_tabHome(){ + lv_obj_t *supmain = tab0; + lv_obj_set_flex_flow(supmain, LV_FLEX_FLOW_COLUMN); + + lv_obj_t *main = lv_obj_create(supmain); + lv_obj_add_style(main, &no_padding, 0); + lv_obj_set_size(main, LV_SIZE_CONTENT, LV_SIZE_CONTENT); + + lv_obj_set_flex_flow(main, LV_FLEX_FLOW_ROW); + lv_obj_set_style_pad_column(main, 1, 0); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_col = lv_obj_create(main); + lv_obj_set_style_pad_all(cont_col, 5, 0); + lv_obj_set_size(cont_col, 250, 400); + lv_obj_align(cont_col, LV_ALIGN_TOP_LEFT, 0, 0); + lv_obj_set_flex_flow(cont_col, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(cont_col, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_col2 = lv_obj_create(main); + lv_obj_set_style_pad_all(cont_col2, 5, 0); + lv_obj_set_flex_align(cont_col2, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_col3 = lv_obj_create(main); + lv_obj_set_style_pad_all(cont_col3, 5, 0); + lv_obj_set_size(cont_col3, 300, 400); + lv_obj_set_flex_flow(cont_col3, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(cont_col3, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER, LV_FLEX_ALIGN_CENTER); + + lv_obj_set_height(cont_col2, 400); + lv_obj_set_width(cont_col2, LV_SIZE_CONTENT); + lv_obj_align_to(cont_col2, cont_col, LV_ALIGN_OUT_TOP_RIGHT, 0, 0); + lv_obj_set_flex_flow(cont_col2, LV_FLEX_FLOW_COLUMN); + lv_obj_set_flex_align(cont_col2, LV_FLEX_ALIGN_END, LV_FLEX_ALIGN_SPACE_BETWEEN, LV_FLEX_ALIGN_SPACE_BETWEEN); + + lv_obj_t *label1 = lv_label_create(cont_col); + lv_obj_set_style_text_font(label1, &montserrat_medium_18, 0); + lv_label_set_text(label1, "Températures"); + lv_obj_set_pos(label1, 0, 0); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_tempExt = lv_obj_create(cont_col); + lv_obj_add_style(cont_tempExt, &style_container, 0); + // lv_obj_set_height(cont_tempExt,50); + lv_obj_set_flex_flow(cont_tempExt, LV_FLEX_FLOW_ROW); + lv_obj_t *lblExt = lv_label_create(cont_tempExt); + lv_label_set_text(lblExt, "ext."); + lv_obj_t *lblTempExt = lv_label_create(cont_tempExt); + lv_obj_add_style(lblTempExt, &style_lbvValue, 0); + lv_label_set_text(lblTempExt, ""); + lv_label_bind_text(lblTempExt, &tempExtSubj, "%s °C"); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_tempInt = lv_obj_create(cont_col); + lv_obj_add_style(cont_tempInt, &style_container, 0); + // lv_obj_set_height(cont_tempInt,50); + lv_obj_set_flex_flow(cont_tempInt, LV_FLEX_FLOW_ROW); + lv_obj_t *lblInt = lv_label_create(cont_tempInt); + lv_label_set_text(lblInt, "int."); + lv_obj_t *lblTempInt = lv_label_create(cont_tempInt); + lv_obj_add_style(lblTempInt, &style_lbvValue, 0); + lv_label_set_text(lblTempInt, ""); + lv_label_bind_text(lblTempInt, &tempIntSubj, "%s °C"); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_tempInt2 = lv_obj_create(cont_col); + lv_obj_add_style(cont_tempInt2, &style_container, 0); + // lv_obj_set_height(cont_tempInt,50); + lv_obj_set_flex_flow(cont_tempInt2, LV_FLEX_FLOW_ROW); + lblInt = lv_label_create(cont_tempInt2); + lv_label_set_text(lblInt, "int."); + lblTempInt2 = lv_label_create(cont_tempInt2); + lv_obj_add_style(lblTempInt2, &style_lbvValue, 0); + lv_obj_set_style_text_font(lblTempInt2,&montserrat_medium_24,0); + + lv_label_set_text(lblTempInt2, ""); + + /*Create a container with COLUMN flex direction*/ + lv_obj_t *cont_Cuve = lv_obj_create(cont_col); + lv_obj_add_style(cont_Cuve, &style_container, 0); + lv_obj_set_flex_flow(cont_Cuve, LV_FLEX_FLOW_ROW_WRAP); + // lv_obj_set_height(cont_Cuve,80); + + lv_obj_t *lblHauteurEau = lv_label_create(cont_Cuve); + lv_label_set_text(lblHauteurEau, "Cuve: "); + lv_obj_t *lblHauteurCuve = lv_label_create(cont_Cuve); + lv_obj_add_style(lblHauteurCuve, &style_lbvValue, 0); + lv_label_bind_text(lblHauteurCuve, &hauteurCuveSubj, "%s cm"); + + lv_obj_t *btnUp = lv_button_create(cont_col2); + lv_obj_add_style(btnUp, &style_btn, 0); + lv_obj_add_event_cb(btnUp, event_handler, LV_EVENT_ALL, upEvent); + lv_obj_align(btnUp, LV_ALIGN_CENTER, 0, -40); + lv_obj_remove_flag(btnUp, LV_OBJ_FLAG_PRESS_LOCK); + lv_obj_t *label = lv_label_create(btnUp); + lv_obj_add_style(label, &style_lbvValue, 0); + lv_label_set_text(label, LV_SYMBOL_UP); + lv_obj_center(label); + + lv_obj_t *btnDwn = lv_button_create(cont_col2); + lv_obj_add_style(btnDwn, &style_btn, 0); + lv_obj_add_event_cb(btnDwn, event_handler, LV_EVENT_ALL, downEvent); + lv_obj_align(btnDwn, LV_ALIGN_CENTER, 0, -40); + lv_obj_remove_flag(btnDwn, LV_OBJ_FLAG_PRESS_LOCK); + label = lv_label_create(btnDwn); + lv_obj_add_style(label, &style_lbvValue, 0); + lv_label_set_text(label, LV_SYMBOL_DOWN); + lv_obj_center(label); + + lv_fragment_manager_t *manager = lv_fragment_manager_create(NULL); + lv_fragment_t *fragment = lv_fragment_create(&meteoforecast_cls, 0); + lv_fragment_manager_add(manager, fragment, &cont_col3); +} + +void draw_tabCuve() +{ + lv_obj_t *imgGraf = lv_image_create(tabCuve); + lv_image_set_src(imgGraf, "A:/sdcard/hello2.png"); +} + +void draw_tabMeteo() +{ + manager2 = lv_fragment_manager_create(NULL); + fragment2 = lv_fragment_create(&meteodailyforecast_cls, (void *)1); + lv_fragment_manager_add(manager2, fragment2, &tabCuve); +} + +void draw_tabVolets() +{ + lv_obj_t *tabMeteo = lv_obj_create(tabVolets); + lv_obj_set_flex_flow(tabMeteo, LV_FLEX_FLOW_COLUMN); + lv_obj_add_style(tabMeteo, &no_padding, 0); + + lv_obj_set_size(tabMeteo, lv_pct(85), lv_pct(100)); + lv_obj_t *cont_rdc = lv_obj_create(tabMeteo); + lv_obj_set_size(cont_rdc, lv_pct(100), lv_pct(100)); + lv_obj_add_style(cont_rdc, &no_padding, 0); + lv_obj_add_style(tabMeteo, &no_padding, 0); + lv_point_t positions_rdc[] = { + {5, 105}, + {55, 45}, + {110, 20}, + {155, 25}, + {225, 45}, + {275, 115}, + {295, 185}}; + lv_obj_t *img = lv_image_create(cont_rdc); + lv_img_set_src(img, &plan_rdc); + float coef = 1.5; + for (size_t i = 1; i < 8; i++) + { + lv_obj_t *btnVolet = lv_checkbox_create(cont_rdc); + lv_obj_set_pos(btnVolet, positions_rdc[i - 1].x * coef, positions_rdc[i - 1].y * coef); + lv_obj_add_style(btnVolet, &style_font_24, 0); + // lv_obj_set_size(btnVolet,100,24); + + // char *nom[10]; + // sprintf(nom,"%d", i); + lv_checkbox_set_text(btnVolet, ""); + } + + lv_obj_t *cont_btn_volets = lv_obj_create(tabVolets); + lv_obj_add_style(cont_btn_volets, &no_padding, 0); + lv_obj_set_size(cont_btn_volets, lv_pct(15), lv_pct(100)); + + lv_obj_set_layout(cont_btn_volets, LV_LAYOUT_GRID); + static int32_t column_dsc[] = {LV_GRID_CONTENT, LV_GRID_TEMPLATE_LAST}; /*2 columns */ + static int32_t row_dsc[] = {LV_GRID_FR(1), LV_GRID_FR(1), LV_GRID_FR(1), LV_GRID_FR(1), LV_GRID_FR(1), LV_GRID_FR(1), LV_GRID_TEMPLATE_LAST}; + lv_obj_set_grid_dsc_array(cont_btn_volets, column_dsc, row_dsc); + + lv_obj_t *btnUp_bis = lv_button_create(cont_btn_volets); + lv_obj_t *lblButtonUp = lv_label_create(btnUp_bis); + lv_label_set_text(lblButtonUp, LV_SYMBOL_UP); + + lv_obj_t *btnDwn_bis = lv_button_create(cont_btn_volets); + lv_obj_t *lblButtonDwn = lv_label_create(btnDwn_bis); + lv_label_set_text(lblButtonDwn, LV_SYMBOL_DOWN); + + lv_obj_set_grid_cell(btnUp_bis, LV_GRID_ALIGN_STRETCH, 0, 1, + LV_GRID_ALIGN_STRETCH, 0, 1); + lv_obj_set_grid_cell(btnDwn_bis, LV_GRID_ALIGN_STRETCH, 0, 1, + LV_GRID_ALIGN_STRETCH, 1, 1); + + lv_obj_t *cont_etage = lv_obj_create(tabMeteo); + lv_obj_set_size(cont_etage, lv_pct(100), lv_pct(100)); + lv_obj_add_style(cont_etage, &no_padding, 0); + + img = lv_image_create(cont_etage); + lv_img_set_src(img, &plan_etage); + + lv_point_t positions_etage[] = { + {100, 15}, + {250, 15}, + {400, 15}, + {480, 300}, + {460, 360}, + {320, 415}}; + for (size_t i = 1; i < 7; i++) + { + lv_obj_t *btnVolet = lv_checkbox_create(cont_etage); + lv_obj_set_pos(btnVolet, positions_etage[i - 1].x, positions_etage[i - 1].y); + lv_obj_add_style(btnVolet, &style_font_24, 0); + // lv_obj_set_size(btnVolet,100,24); + + // char *nom[10]; + // sprintf(nom,"%d", i); + lv_checkbox_set_text(btnVolet, ""); + } +} + +/* ------------------------------------------------------------ */ +/* Dessin IHM */ +/* ------------------------------------------------------------ */ +void draw_ihm() +{ + lv_subject_init_string(&tempExtSubj, tempExtStr, NULL, 6, "--"); + lv_subject_init_string(&tempIntSubj, tempIntStr, NULL, 6, "--"); + lv_subject_init_string(&hauteurCuveSubj, hauteurCuveStr, NULL, 9, "--"); + lv_subject_init_string(&hauteurCuveEvolSubj, hauteurCuveEvolStr, NULL, 9, "--"); + + struct meteodailyforecast_data d; + struct dailyforecast_prev p; + lv_strcpy(p.desc, ""); + d.previsions = p; + lv_subject_init_pointer(&forecastD1Subj, &d); + lv_subject_init_pointer(&forecastD2Subj, &d); + lv_subject_init_pointer(&forecastD3Subj, &d); + + struct meteoforecast_data d1; + struct forecast_prev p1; + lv_strcpy(p1.desc, ""); + + d1.previsions = p1; + lv_subject_init_pointer(&forecastH1Subj, &d1); + lv_subject_init_pointer(&forecastH2Subj, &d1); + lv_subject_init_pointer(&forecastH3Subj, &d1); + + // keys.clear(); + lv_obj_clean(lv_scr_act()); + + /*Create a Tab view object*/ + lv_obj_t *tabview; + tabview = lv_tabview_create(lv_screen_active()); + lv_tabview_set_tab_bar_position(tabview, LV_DIR_LEFT); + lv_tabview_set_tab_bar_size(tabview, 80); + lv_obj_add_event_cb(tabview, tabChgEvt, LV_EVENT_VALUE_CHANGED, tabview); /* Assign an event callback */ + + // lv_obj_set_style_bg_color(tabview, lv_palette_lighten(LV_PALETTE_RED, 2), 0); + + lv_obj_t *tab_buttons = lv_tabview_get_tab_bar(tabview); + lv_obj_set_width(tab_buttons, 100); + lv_obj_set_style_text_font(tab_buttons, &montserrat_medium_24, 0); + lv_obj_set_style_bg_color(tab_buttons, lv_palette_darken(LV_PALETTE_GREY, 3), 0); + lv_obj_set_style_text_color(tab_buttons, lv_palette_lighten(LV_PALETTE_GREY, 5), 0); + lv_obj_set_style_border_side(tab_buttons, LV_BORDER_SIDE_RIGHT, LV_PART_ITEMS | LV_STATE_CHECKED); + + /*Add 3 tabs (the tabs are page (lv_page) and can be scrolled*/ + tab0 = lv_tabview_add_tab(tabview, LV_SYMBOL_HOME); + tabVolets = lv_tabview_add_tab(tabview, "Volets"); + tabMeteo = lv_tabview_add_tab(tabview, "Météo"); + tabCuve = lv_tabview_add_tab(tabview, "\xEF\x95\xB5" + "Cuve"); + tabSettings = lv_tabview_add_tab(tabview, "Settings"); + + // lv_obj_set_style_bg_color(tab2b, lv_palette_lighten(LV_PALETTE_AMBER, 3), 0); + lv_obj_set_style_bg_opa(tabVolets, LV_OPA_COVER, 0); + + lv_style_init(&style_btn); + + lv_style_init(&style_font_24); + lv_style_set_text_font(&style_font_24, &montserrat_medium_24); + + lv_style_init(&style_font_12); + lv_style_set_text_font(&style_font_12, &montserrat_medium_12); + + // lv_style_set_bg_color(&style_btn, lv_color_hex(0x115588)); + // lv_style_set_bg_opa(&style_btn, LV_OPA_50); + // lv_style_set_border_width(&style_btn, 2); + // lv_style_set_border_color(&style_btn, lv_color_black()); + lv_style_set_width(&style_btn, 80); + lv_style_set_height(&style_btn, 100); + + // Un style pour les conteneurs (température, cuve ...) + lv_style_init(&style_container); + lv_style_set_pad_all(&style_container, 5); + // lv_style_set_height(&style_container,LV_SIZE_CONTENT); + lv_style_set_height(&style_container, 80); + lv_style_set_width(&style_container, 200); + lv_style_set_bg_color(&style_container, lv_palette_lighten(LV_PALETTE_BLUE_GREY, 4)); + lv_style_set_align(&style_container, LV_ALIGN_BOTTOM_LEFT); + lv_style_set_flex_cross_place(&style_container, LV_FLEX_ALIGN_END); + + static lv_style_t no_padding; + lv_style_init(&no_padding); + lv_style_set_pad_all(&no_padding, 0); + + lv_style_init(&style_lbvValue); + lv_style_set_text_font(&style_lbvValue, &lv_font_montserrat_40); + + draw_tabHome(); + + lv_obj_set_flex_flow(tabVolets, LV_FLEX_FLOW_ROW); + + lv_obj_set_flex_flow(tabMeteo, LV_FLEX_FLOW_COLUMN); +} + +void weather_data_retreived_start() +{ + if (lvgl_port_lock(0)) + { + lv_subject_set_int(&meteoStatus, 1); + lvgl_port_unlock(); + } +} + +void weather_data_retreived(struct meteodailyforecast_data dailyDatas[3], struct meteoforecast_data datas[3]) +{ + /* + ESP_LOGE(TAG, "debut debug"); + printf("%lld\n", datas[0].datetime); + printf("%s\n", datas[0].previsions.desc); + printf("%f\n", datas[0].previsions.min); + printf("%lld\n", datas[1].datetime); + printf("%s\n", datas[1].previsions.desc); + printf("%f\n", datas[1].previsions.min); + printf("%lld\n", datas[2].datetime); + printf("%s\n", datas[2].previsions.desc); + printf("%f\n", datas[2].previsions.min); + ESP_LOGE(TAG, "fin debug"); + */ + if (lvgl_port_lock(0)) + { + ESP_LOGV("MeteoFrance", "------------------------------------- Set des subjects J --------------------------------"); + // Prévisions des 3 prochains jours + lv_subject_set_pointer(&forecastD1Subj, &dailyDatas[0]); + lv_subject_set_pointer(&forecastD2Subj, &dailyDatas[1]); + lv_subject_set_pointer(&forecastD3Subj, &dailyDatas[2]); + + ESP_LOGV("MeteoFrance", "------------------------------------- Set des subjects H--------------------------------"); + // Prévisions des 3 prochains jours + ESP_LOGV("MeteoFrance", "Pointeur %lli", datas[0].datetime); + lv_subject_set_pointer(&forecastH1Subj, &datas[0]); + lv_subject_set_pointer(&forecastH2Subj, &datas[1]); + lv_subject_set_pointer(&forecastH3Subj, &datas[2]); + + lv_subject_set_int(&meteoStatus, 0); + lvgl_port_unlock(); + // ESP_LOGE(TAG, "------------------------------------- Fin Set des subjects --------------------------------"); + } +} + +void mount_sd_card() +{ + // Options for mounting the filesystem. + // If format_if_mount_failed is set to true, SD card will be partitioned and + // formatted in case when mounting fails. + esp_vfs_fat_sdmmc_mount_config_t mount_config = { + .format_if_mount_failed = false, + .max_files = 5, + .allocation_unit_size = 16 * 1024}; + sdmmc_card_t *card; + const char mount_point[] = MOUNT_POINT; + ESP_LOGI(TAG, "Initializing SD card"); + + ESP_LOGI(TAG, "Using SPI peripheral"); + + sdmmc_host_t host = SDSPI_HOST_DEFAULT(); + + spi_bus_config_t bus_cfg = { + .mosi_io_num = PIN_NUM_MOSI, + .miso_io_num = PIN_NUM_MISO, + .sclk_io_num = PIN_NUM_CLK, + .quadwp_io_num = -1, + .quadhd_io_num = -1, + .max_transfer_sz = 4000, + }; + esp_err_t ret = spi_bus_initialize(host.slot, &bus_cfg, SDSPI_DEFAULT_DMA); + if (ret != ESP_OK) + { + ESP_LOGE(TAG, "Failed to initialize bus."); + return; + } + + sdspi_device_config_t slot_config = SDSPI_DEVICE_CONFIG_DEFAULT(); + slot_config.gpio_cs = PIN_NUM_CS; + slot_config.host_id = host.slot; + + ESP_LOGI(TAG, "Mounting filesystem"); + ret = esp_vfs_fat_sdspi_mount(mount_point, &host, &slot_config, &mount_config, &card); + + if (ret != ESP_OK) + { + if (ret == ESP_FAIL) + { + ESP_LOGE(TAG, "Failed to mount filesystem. " + "If you want the card to be formatted, set the CONFIG_EXAMPLE_FORMAT_IF_MOUNT_FAILED menuconfig option."); + } + else + { + ESP_LOGE(TAG, "Failed to initialize the card (%s). " + "Make sure SD card lines have pull-up resistors in place.", + esp_err_to_name(ret)); + } + return; + } + ESP_LOGI(TAG, "Filesystem mounted"); + + // Card has been initialized, print its properties + sdmmc_card_print_info(stdout, card); +} + +extern char *days[7]; +extern char *months[12]; + +static void updateTime(void *pvParameter) +{ + + char strftime_buf[64]; + time_t now = 0; + while (1) + { + time(&now); + struct tm timeinfo = {0}; + localtime_r(&now, &timeinfo); + sprintf(strftime_buf, "%s %d %s %02d:%02d", days[timeinfo.tm_wday], timeinfo.tm_mday, months[timeinfo.tm_mon], timeinfo.tm_hour, timeinfo.tm_min); + if(lvgl_port_lock(0)){ + lv_subject_copy_string(&dateHeureSubj, strftime_buf); + lvgl_port_unlock(); + } + /* + lv_obj_refr_size(lv_obj_get_child(lv_obj_get_child(lv_layer_top(),0),0)); + lv_obj_refr_size(lv_obj_get_child(lv_layer_top(),0)); + lvgl_port_unlock(); + }*/ + vTaskDelay(60000 / portTICK_PERIOD_MS); + } +} + +esp_err_t _ota_http_event_handler(esp_http_client_event_t *evt) +{ + switch (evt->event_id) { + case HTTP_EVENT_ERROR: + ESP_LOGD(TAG, "HTTP_EVENT_ERROR"); + break; + case HTTP_EVENT_ON_CONNECTED: + ESP_LOGD(TAG, "HTTP_EVENT_ON_CONNECTED"); + break; + case HTTP_EVENT_HEADER_SENT: + ESP_LOGD(TAG, "HTTP_EVENT_HEADER_SENT"); + break; + case HTTP_EVENT_ON_HEADER: + ESP_LOGD(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value); + break; + case HTTP_EVENT_ON_DATA: + ESP_LOGD(TAG, "HTTP_EVENT_ON_DATA, len=%d", evt->data_len); + break; + case HTTP_EVENT_ON_FINISH: + ESP_LOGD(TAG, "HTTP_EVENT_ON_FINISH"); + break; + case HTTP_EVENT_DISCONNECTED: + ESP_LOGD(TAG, "HTTP_EVENT_DISCONNECTED"); + break; + case HTTP_EVENT_REDIRECT: + ESP_LOGD(TAG, "HTTP_EVENT_REDIRECT"); + break; + } + return ESP_OK; +} + +extern const uint8_t server_cert_pem_start[] asm("_binary_ca_cert_pem_start"); +extern const uint8_t server_cert_pem_end[] asm("_binary_ca_cert_pem_end"); + +void simple_ota_example_task(void *pvParameter) +{ + ESP_LOGI(TAG, "Starting OTA example task"); +#ifdef CONFIG_EXAMPLE_FIRMWARE_UPGRADE_BIND_IF + esp_netif_t *netif = get_example_netif_from_desc(bind_interface_name); + if (netif == NULL) { + ESP_LOGE(TAG, "Can't find netif from interface description"); + abort(); + } + struct ifreq ifr; + esp_netif_get_netif_impl_name(netif, ifr.ifr_name); + ESP_LOGI(TAG, "Bind interface name is %s", ifr.ifr_name); +#endif + esp_http_client_config_t config = { + .url = "https://192.168.0.28:8070/rgb_lcd.bin", + .event_handler = _ota_http_event_handler, + .keep_alive_enable = true, + .cert_pem = (char *)server_cert_pem_start, +#ifdef CONFIG_EXAMPLE_FIRMWARE_UPGRADE_BIND_IF + .if_name = &ifr, +#endif + }; + +#ifdef CONFIG_EXAMPLE_FIRMWARE_UPGRADE_URL_FROM_STDIN + char url_buf[OTA_URL_SIZE]; + if (strcmp(config.url, "FROM_STDIN") == 0) { + example_configure_stdin_stdout(); + fgets(url_buf, OTA_URL_SIZE, stdin); + int len = strlen(url_buf); + url_buf[len - 1] = '\0'; + config.url = url_buf; + } else { + ESP_LOGE(TAG, "Configuration mismatch: wrong firmware upgrade image url"); + abort(); + } +#endif + +#ifdef CONFIG_EXAMPLE_SKIP_COMMON_NAME_CHECK + config.skip_cert_common_name_check = true; +#endif + + esp_https_ota_config_t ota_config = { + .http_config = &config, + }; + ESP_LOGI(TAG, "Attempting to download update from %s", config.url); + esp_err_t ret = esp_https_ota(&ota_config); + if (ret == ESP_OK) { + ESP_LOGI(TAG, "OTA Succeed, Rebooting..."); + esp_restart(); + } else { + ESP_LOGE(TAG, "Firmware upgrade failed"); + } + while (1) { + vTaskDelay(1000 / portTICK_PERIOD_MS); + } +} + + + am2302_handle_t sensor = NULL; + +void readTempHumid(void *pvParameter) +{ + float temperature = 0; + float humidity = 0; + while (1) + { + am2302_read_temp_humi(sensor, &temperature, &humidity); + char buff[40]; + ESP_LOGI(TAG, "Temperature: %.1f °C, Humidity: %.1f %%", temperature, humidity); + sprintf(buff,"%.1f °C, %.1f %%", temperature, humidity); + if(lvgl_port_lock(0)){ + lv_label_set_text(lblTempInt2,buff); + lvgl_port_unlock(); + } + vTaskDelay(60000 / portTICK_PERIOD_MS); + } + +} + +void app_main(void) +{ + printf("Minimum free heap size: %" PRIu32 " bytes\n", esp_get_minimum_free_heap_size()); + printf("Free heap size: %" PRIu32 " bytes\n", esp_get_free_heap_size()); + + printf("1- Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + + esp_log_level_set("wifi", ESP_LOG_ERROR); + + printf("2- Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + + mount_sd_card(); + + esp_vfs_littlefs_conf_t conf = { + .base_path = "/littlefs", + .partition_label = "littlefs", + .format_if_mount_failed = true, + .dont_mount = false, + }; + + printf("3 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + /* LCD HW initialization */ + ESP_ERROR_CHECK(app_lcd_init()); + + printf("4 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + /* Touch initialization */ + ESP_ERROR_CHECK(app_touch_init()); + + printf("5 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + /* LVGL initialization */ + ESP_ERROR_CHECK(app_lvgl_init()); + + printf("6 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + + lv_subject_init_int(&meteoStatus, -1); + + /* On affiche au plus tot l'ecran de démarrage */ + if (lvgl_port_lock(0)) + { + // ESP_ERROR_CHECK(esp_lcd_panel_mirror(lcd_panel,true,true)); + app_main_display(); + lvgl_port_unlock(); + } + + printf("7 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + // Initialize NVS + esp_err_t ret = nvs_flash_init(); + if (ret == ESP_ERR_NVS_NO_FREE_PAGES || ret == ESP_ERR_NVS_NEW_VERSION_FOUND) + { + ESP_ERROR_CHECK(nvs_flash_erase()); + ret = nvs_flash_init(); + } + ESP_ERROR_CHECK(ret); + + printf("8 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + ESP_LOGI(TAG, "ESP_WIFI_MODE_STA"); + wifi_init_sta(); + start_wifi_logger(); + wifi_log_e("test", "%s %d %f", "hello world wifi logger", 43, 45.341223242); // write log over wifi with log level -> ERROR + esp_log_level_set("tcp_handler", ESP_LOG_NONE); + printf("8b - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + mqtt_app_start(); + + printf("9 - Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + + time_t now; + struct tm timeinfo; + time(&now); + localtime_r(&now, &timeinfo); + // Is time set? If not, tm_year will be (1970 - 1900). + if (timeinfo.tm_year < (2016 - 1900)) + { + ESP_LOGI(TAG, "Time is not set yet. Connecting to WiFi and getting time over NTP."); + obtain_time(); + // update 'now' variable with current time + time(&now); + } + + char strftime_buf[64]; + + // Set timezone to Eastern Standard Time and print local time + setenv("TZ", "CET-1CEST,M3.5.0,M10.5.0/3", 1); + tzset(); + localtime_r(&now, &timeinfo); + strftime(strftime_buf, sizeof(strftime_buf), "%c", &timeinfo); + + printf("10. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + heap_caps_print_heap_info(MALLOC_CAP_INTERNAL | MALLOC_CAP_8BIT); + + on_weather_data_retrieval(weather_data_retreived); + on_weather_data_retrieval_start(weather_data_retreived_start); + initialise_weather_data_retrieval(600000); + ESP_LOGW(TAG, "Weather data retrieval initialized"); + + printf("11. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + ESP_LOGW(TAG, "On telecharge l'image cuve"); + TaskHandle_t xHandle = NULL; + BaseType_t ret1; + + ret1 = xTaskCreate(&imgdwn, "imageDownload_task", 3 * 1024, NULL, 5, &xHandle); + if (ret1 != pdPASS) + { + ESP_LOGE(TAG, "Impossiblke de creer la tache imageDownload_task %i", ret1); + } + + BaseType_t ret2 = xTaskCreate(&updateTime, "updateTimeTask", 3 * 1024, NULL, 5, NULL); + if (ret2 != pdPASS) + { + ESP_LOGE(TAG, "Impossiblke de creer la tache updateTimeTask %i", ret1); + } + + printf("12. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + /* Show LVGL objects */ + if (lvgl_port_lock(0)) + { + draw_ihm(); + // lv_disp_set_rotation(lvgl_disp, LV_DISPLAY_ROTATION_180); + + lvgl_port_unlock(); + } + printf("13. Free heap after buffers allocation: %d\n", xPortGetFreeHeapSize()); + printf("Minimum free heap size: %" PRIu32 " bytes\n", esp_get_minimum_free_heap_size()); + printf("Free heap size: %" PRIu32 " bytes\n", esp_get_free_heap_size()); + LV_ASSERT_MEM_INTEGRITY(); + + lv_mem_monitor_t mon; + lv_mem_monitor(&mon); + printf("used: %6d (%3d %%), frag: %3d %%, biggest free: %6d\n", + (int)mon.total_size - mon.free_size, mon.used_pct, mon.frag_pct, + (int)mon.free_biggest_size); + + ESP_LOGI(TAG, "Initializing LittleFS"); + + esp_vfs_littlefs_conf_t conflfs = { + .base_path = "/littlefs", + .partition_label = "littlefs", + .format_if_mount_failed = true, + .dont_mount = false, + }; + + // Use settings defined above to initialize and mount LittleFS filesystem. + // Note: esp_vfs_littlefs_register is an all-in-one convenience function. + ret = esp_vfs_littlefs_register(&conflfs); + + if (ret != ESP_OK) + { + if (ret == ESP_FAIL) + { + ESP_LOGE(TAG, "Failed to mount or format filesystem"); + } + else if (ret == ESP_ERR_NOT_FOUND) + { + ESP_LOGE(TAG, "Failed to find LittleFS partition"); + } + else + { + ESP_LOGE(TAG, "Failed to initialize LittleFS (%s)", esp_err_to_name(ret)); + } + return; + } + + size_t total = 0, used = 0; + ret = esp_littlefs_info(conflfs.partition_label, &total, &used); + if (ret != ESP_OK) + { + ESP_LOGE(TAG, "Failed to get LittleFS partition information (%s)", esp_err_to_name(ret)); + } + else + { + ESP_LOGI(TAG, "Partition size: total: %d, used: %d", total, used); + } + + ESP_LOGI(TAG, "Reading file"); + FILE *f = fopen("/littlefs/p1j.png", "r"); + if (f == NULL) + { + ESP_LOGE(TAG, "Failed to open file for reading"); + return; + } + + char line[128]; + char *pos; + + fgets(line, sizeof(line), f); + fclose(f); + // strip newline + pos = strchr(line, '\n'); + if (pos) + { + *pos = '\0'; + } + ESP_LOGI(TAG, "Read from file: '%s'", line); + + //OTA désactivé + //xTaskCreate(&simple_ota_example_task, "ota_example_task", 8192, NULL, 5, NULL); + + /* Configuration de la sonde Temp/Humid.*/ + am2302_config_t am2302_config = { + .gpio_num = AM2302_GPIO, + }; + am2302_rmt_config_t rmt_config = { + .clk_src = RMT_CLK_SRC_DEFAULT, + }; + ESP_ERROR_CHECK(am2302_new_sensor_rmt(&am2302_config, &rmt_config, &sensor)); + + + xTaskCreate(&readTempHumid, "read_temp_task", 8192, NULL, 5, NULL); + + +} diff --git a/main/main.h b/main/main.h index 16b7090..d95dfb1 100644 --- a/main/main.h +++ b/main/main.h @@ -1,3 +1,13 @@ -#pragma once -#include "mqtt_client.h" -static void showMeteoIcon(const char *icon, lv_obj_t *desc_icon, int childNr); +#pragma once +#include "mqtt_client.h" +static void showMeteoIcon(const char *icon, lv_obj_t *desc_icon, int childNr); + +static void draw_tabVolets(); + +static void draw_tabMeteo(); + +static void tabChgEvt(lv_event_t *event); + +static void draw_tabCuve(); +static void draw_tabHome(); +static void draw_tabSettings(); diff --git a/main/mqtt.c b/main/mqtt.c index 45ade4e..04ab249 100644 --- a/main/mqtt.c +++ b/main/mqtt.c @@ -1,290 +1,298 @@ -#include "mqtt.h" -#include "esp_log.h" -#include "esp_lvgl_port.h" -#include "mqtt_client.h" - -esp_mqtt_client_handle_t client; -lv_subject_t mqttStatus; - -extern lv_subject_t tempIntSubj; -extern lv_subject_t tempExtSubj; -extern lv_subject_t hauteurCuveSubj; -extern lv_subject_t hauteurCuveEvolSubj; - -static const char *TAG = "mqtt"; - -char *upEvent = "monter"; -char *downEvent = "descendre"; - -char *topicTempExt = "house/temp/282A802600008059"; -char *topicHauteurCuve = "house/cuve/hauteur"; -char *topicTempInt = "house/temp/287DCF1E00008020"; -char *topicHauteurCuveEvol = "house/cuve/hauteurEvol"; -char *topicTest = "test"; - -LV_IMAGE_DECLARE(mqtt_ok); -LV_IMAGE_DECLARE(mqtt_ko); - -static void mqttStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject); - -static void mqttStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject) -{ - ESP_LOGE(TAG, "On passe dans le callback de chgt de statut; %li", lv_subject_get_int(subject)); - if(lvgl_port_lock(0)){ - lv_obj_t * wifiSt = lv_obj_get_child(lv_obj_get_child(lv_layer_top(), 0),3); - if(lv_obj_check_type(wifiSt, &lv_image_class)){ - switch (lv_subject_get_int(subject)) - { - case 0: - lv_image_set_src(wifiSt,&mqtt_ko); - break; - case 1: - lv_image_set_src(wifiSt,&mqtt_ok); - break; - case 2: - lv_color_t color = lv_color_make(255, 0, 0); - lv_obj_set_style_image_recolor_opa(wifiSt, 125, 0); - lv_obj_set_style_image_recolor(wifiSt, color, 0); - vTaskDelay(2000 / portTICK_PERIOD_MS); - - break; - case 3: - lv_obj_set_style_image_recolor_opa(wifiSt, 0, 0); - break; - default: - break; - } - }else{ - ESP_LOGE(TAG, "L'objet recuip en semble pas etre du bon type"); - } - lvgl_port_unlock(); - } - //int32_t prev_v = lv_subject_get_previous_int(subject); - //int32_t cur_v = lv_subject_get_int(subject); - - //lv_obj_t * btn = lv_observer_get_target(observer); -} - -static void log_error_if_nonzero(const char *message, int error_code) -{ - if (error_code != 0) - { - ESP_LOGE(TAG, "Last error %s: 0x%x", message, error_code); - } -} - -void splitIt(char *payload, unsigned int length, float *datas) -{ - char *sep = ","; - char *token; - char *saveptr1; - - token = strtok_r(payload, sep, &saveptr1); - datas[0] = atoff(token); - ESP_LOGE(TAG,"%f",datas[0]); - - token = strtok_r(NULL, sep, &saveptr1); - datas[1] = atoff(token); - ESP_LOGE(TAG,"%f",datas[1]); - - token = strtok_r(NULL, sep, &saveptr1); - datas[2] = atoff(token); - ESP_LOGE(TAG,"%f",datas[2]); - - token = strtok_r(NULL, sep, &saveptr1); - datas[3] = atoff(token); - ESP_LOGE(TAG,"%f",datas[3]); -} - -/* - * @brief Event handler registered to receive MQTT events - * - * This function is called by the MQTT client event loop. - * - * @param handler_args user data registered to the event. - * @param base Event base for the handler(always MQTT Base in this example). - * @param event_id The id for the received event. - * @param event_data The data for the event, esp_mqtt_event_handle_t. - */ -static void mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, void *event_data) -{ - ESP_LOGD(TAG, "Event dispatched from event loop base=%s, event_id=%" PRIi32 "", base, event_id); - esp_mqtt_event_handle_t event = event_data; - esp_mqtt_client_handle_t client = event->client; - int msg_id; - switch ((esp_mqtt_event_id_t)event_id) - { - case MQTT_EVENT_CONNECTED: - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut mqttStatus 1"); - lv_subject_set_int(&mqttStatus,1); - lvgl_port_unlock(); - } - ESP_LOGI(TAG, "MQTT_EVENT_CONNECTED"); - //msg_id = esp_mqtt_client_publish(client, "/topic/qos1", "data_3", 0, 1, 0); - //ESP_LOGI(TAG, "sent publish successful, msg_id=%d", msg_id); - - msg_id = esp_mqtt_client_subscribe(client, topicTempExt, 0); - ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); - - msg_id = esp_mqtt_client_subscribe(client, topicTempInt, 0); - ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); - - msg_id = esp_mqtt_client_subscribe(client, topicHauteurCuve, 0); - ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); - - msg_id = esp_mqtt_client_subscribe(client, topicHauteurCuveEvol, 0); - ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); - - msg_id = esp_mqtt_client_subscribe(client, topicTest, 0); - ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); - - //msg_id = esp_mqtt_client_subscribe(client, "/topic/qos1", 1); - //ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); - - //msg_id = esp_mqtt_client_unsubscribe(client, "/topic/qos1"); - //ESP_LOGI(TAG, "sent unsubscribe successful, msg_id=%d", msg_id); - break; - case MQTT_EVENT_DISCONNECTED: - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut mqttStatus 0"); - lv_subject_set_int(&mqttStatus,0); - lvgl_port_unlock(); - } - ESP_LOGI(TAG, "MQTT_EVENT_DISCONNECTED"); - break; - - case MQTT_EVENT_SUBSCRIBED: - ESP_LOGI(TAG, "MQTT_EVENT_SUBSCRIBED, msg_id=%d", event->msg_id); - //msg_id = esp_mqtt_client_publish(client, "/topic/qos0", "data", 0, 0, 0); - //ESP_LOGI(TAG, "sent publish successful, msg_id=%d", msg_id); - break; - case MQTT_EVENT_UNSUBSCRIBED: - ESP_LOGI(TAG, "MQTT_EVENT_UNSUBSCRIBED, msg_id=%d", event->msg_id); - break; - case MQTT_EVENT_PUBLISHED: - ESP_LOGI(TAG, "MQTT_EVENT_PUBLISHED, msg_id=%d", event->msg_id); - break; - case MQTT_EVENT_DATA: - lv_subject_set_int(&mqttStatus,2); - ESP_LOGI(TAG, "MQTT_EVENT_DATA"); - printf("TOPIC=%.*s\r\n", event->topic_len, event->topic); - printf("DATA=%.*s\r\n", event->data_len, event->data); - if (strncmp(event->topic, topicTempExt, 27) == 0) - { - lvgl_port_lock(0); - // on retransforme en float pour ne garder que la partie entiere de la température - float temp = strtof(event->data, NULL); - char buff[5]; - sprintf(buff,"%.1f",temp); - lv_subject_copy_string(&tempExtSubj, buff); - lvgl_port_unlock(); - } - else if (strncmp(event->topic, topicTempInt, 27) == 0) - { - lvgl_port_lock(0); - // on retransforme en float pour ne garder que la partie entiere de la température - float temp = strtof(event->data, NULL); - char buff[5]; - sprintf(buff,"%.1f",temp); - lv_subject_copy_string(&tempIntSubj, buff); - lvgl_port_unlock(); - } - else if (strncmp(event->topic, topicHauteurCuveEvol, 22) == 0) - { - /* float datas[4] = {}; - splitIt(event->data, event->data_len, datas); - ser1->y_points[0] = 130 - (int)datas[0]; - ser1->y_points[1] = 130 - (int)datas[1]; - ser1->y_points[2] = 130 - (int)datas[2]; - ser1->y_points[3] = 130 - (int)datas[3]; - lvgl_port_lock(0); - lv_chart_refresh(chart); - lvgl_port_unlock(); - */ - - // lv_subject_copy_string(&hauteurCuveEvolSubj, event->data); - } - else if (strncmp(event->topic, topicHauteurCuve, 18) == 0) - { - lvgl_port_lock(0); - char *datas = NULL; - datas = (char *)malloc(event->data_len * sizeof(char)); - stpncpy(datas, event->data, event->data_len); - datas[event->data_len] = '\0'; - lv_subject_copy_string(&hauteurCuveSubj, datas); - free(datas); - lvgl_port_unlock(); - }else if (strncmp(event->topic, topicTest, 4) == 0){ - ESP_LOGE(TAG,"Msg reecu sur test"); - } - - else - { - ESP_LOGE(TAG, "None match :-("); - } - lv_subject_set_int(&mqttStatus,3); - break; - case MQTT_EVENT_ERROR: - ESP_LOGI(TAG, "MQTT_EVENT_ERROR"); - if (event->error_handle->error_type == MQTT_ERROR_TYPE_TCP_TRANSPORT) - { - log_error_if_nonzero("reported from esp-tls", event->error_handle->esp_tls_last_esp_err); - log_error_if_nonzero("reported from tls stack", event->error_handle->esp_tls_stack_err); - log_error_if_nonzero("captured as transport's socket errno", event->error_handle->esp_transport_sock_errno); - ESP_LOGI(TAG, "Last errno string (%s)", strerror(event->error_handle->esp_transport_sock_errno)); - } - break; - default: - ESP_LOGI(TAG, "Other event id:%d", event->event_id); - break; - } -} -void mqtt_app_start(void) -{ - - lv_subject_init_int(&mqttStatus,-1); - lv_subject_add_observer_obj(&mqttStatus, mqttStatus_obs_cb, NULL, NULL); - - - esp_mqtt_client_config_t mqtt_cfg = { - .broker.address.uri = "mqtt://192.168.0.10", - .network.timeout_ms = 1000}; -#if CONFIG_BROKER_URL_FROM_STDIN - char line[128]; - - if (strcmp(mqtt_cfg.broker.address.uri, "FROM_STDIN") == 0) - { - int count = 0; - printf("Please enter url of mqtt broker\n"); - while (count < 128) - { - int c = fgetc(stdin); - if (c == '\n') - { - line[count] = '\0'; - break; - } - else if (c > 0 && c < 127) - { - line[count] = c; - ++count; - } - vTaskDelay(10 / portTICK_PERIOD_MS); - } - mqtt_cfg.broker.address.uri = line; - printf("Broker url: %s\n", line); - } - else - { - ESP_LOGE(TAG, "Configuration mismatch: wrong broker url"); - abort(); - } -#endif /* CONFIG_BROKER_URL_FROM_STDIN */ - - client = esp_mqtt_client_init(&mqtt_cfg); - /* The last argument may be used to pass data to the event handler, in this example mqtt_event_handler */ - esp_mqtt_client_register_event(client, ESP_EVENT_ANY_ID, mqtt_event_handler, NULL); - esp_mqtt_client_start(client); -} - +#include "mqtt.h" +#include "esp_log.h" +#include "esp_lvgl_port.h" +#include "mqtt_client.h" + +esp_mqtt_client_handle_t client; +lv_subject_t mqttStatus; + +extern lv_subject_t tempIntSubj; +extern lv_subject_t tempExtSubj; +extern lv_subject_t hauteurCuveSubj; +extern lv_subject_t hauteurCuveEvolSubj; + +static const char *TAG = "domo_mqtt"; + +char *upEvent = "monter"; +char *downEvent = "descendre"; + +char *topicTempExt = "house/temp/282A802600008059"; +char *topicHauteurCuve = "house/cuve/hauteur"; +char *topicTempInt = "house/temp/287DCF1E00008020"; +char *topicHauteurCuveEvol = "house/cuve/hauteurEvol"; +char *topicdomoticCommand = "domotic/cmd"; +char *topicTest = "test"; + +LV_IMAGE_DECLARE(mqtt_ok); +LV_IMAGE_DECLARE(mqtt_ko); + +static void mqttStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject); + +static void mqttStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject) +{ + ESP_LOGV(TAG, "On passe dans le callback de chgt de statut; %li", lv_subject_get_int(subject)); + if(lvgl_port_lock(0)){ + lv_obj_t * wifiSt = lv_obj_get_child(lv_obj_get_child(lv_layer_top(), 0),3); + if(lv_obj_check_type(wifiSt, &lv_image_class)){ + switch (lv_subject_get_int(subject)) + { + case 0: + lv_image_set_src(wifiSt,&mqtt_ko); + break; + case 1: + lv_image_set_src(wifiSt,&mqtt_ok); + break; + case 2: + lv_color_t color = lv_color_make(255, 0, 0); + lv_obj_set_style_image_recolor_opa(wifiSt, 125, 0); + lv_obj_set_style_image_recolor(wifiSt, color, 0); + vTaskDelay(2000 / portTICK_PERIOD_MS); + + break; + case 3: + lv_obj_set_style_image_recolor_opa(wifiSt, 0, 0); + break; + default: + break; + } + }else{ + ESP_LOGE(TAG, "L'objet recuip en semble pas etre du bon type"); + } + lvgl_port_unlock(); + } + //int32_t prev_v = lv_subject_get_previous_int(subject); + //int32_t cur_v = lv_subject_get_int(subject); + + //lv_obj_t * btn = lv_observer_get_target(observer); +} + +static void log_error_if_nonzero(const char *message, int error_code) +{ + if (error_code != 0) + { + ESP_LOGE(TAG, "Last error %s: 0x%x", message, error_code); + } +} + +void splitIt(char *payload, unsigned int length, float *datas) +{ + char *sep = ","; + char *token; + char *saveptr1; + + token = strtok_r(payload, sep, &saveptr1); + datas[0] = atoff(token); + ESP_LOGE(TAG,"%f",datas[0]); + + token = strtok_r(NULL, sep, &saveptr1); + datas[1] = atoff(token); + ESP_LOGE(TAG,"%f",datas[1]); + + token = strtok_r(NULL, sep, &saveptr1); + datas[2] = atoff(token); + ESP_LOGE(TAG,"%f",datas[2]); + + token = strtok_r(NULL, sep, &saveptr1); + datas[3] = atoff(token); + ESP_LOGE(TAG,"%f",datas[3]); +} + +/* + * @brief Event handler registered to receive MQTT events + * + * This function is called by the MQTT client event loop. + * + * @param handler_args user data registered to the event. + * @param base Event base for the handler(always MQTT Base in this example). + * @param event_id The id for the received event. + * @param event_data The data for the event, esp_mqtt_event_handle_t. + */ +static void mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, void *event_data) +{ + ESP_LOGV(TAG, "Event dispatched from event loop base=%s, event_id=%" PRIi32 "", base, event_id); + esp_mqtt_event_handle_t event = event_data; + esp_mqtt_client_handle_t client = event->client; + int msg_id; + switch ((esp_mqtt_event_id_t)event_id) + { + case MQTT_EVENT_CONNECTED: + if(lvgl_port_lock(0)){ + ESP_LOGV(TAG,"Statut mqttStatus 1"); + lv_subject_set_int(&mqttStatus,1); + lvgl_port_unlock(); + } + ESP_LOGI(TAG, "MQTT_EVENT_CONNECTED"); + //msg_id = esp_mqtt_client_publish(client, "/topic/qos1", "data_3", 0, 1, 0); + //ESP_LOGI(TAG, "sent publish successful, msg_id=%d", msg_id); + + msg_id = esp_mqtt_client_subscribe(client, topicTempExt, 0); + ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + msg_id = esp_mqtt_client_subscribe(client, topicTempInt, 0); + ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + msg_id = esp_mqtt_client_subscribe(client, topicHauteurCuve, 0); + ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + msg_id = esp_mqtt_client_subscribe(client, topicHauteurCuveEvol, 0); + ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + msg_id = esp_mqtt_client_subscribe(client, topicTest, 0); + ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + msg_id = esp_mqtt_client_subscribe(client, topicdomoticCommand, 0); + ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + //msg_id = esp_mqtt_client_subscribe(client, "/topic/qos1", 1); + //ESP_LOGI(TAG, "sent subscribe successful, msg_id=%d", msg_id); + + //msg_id = esp_mqtt_client_unsubscribe(client, "/topic/qos1"); + //ESP_LOGI(TAG, "sent unsubscribe successful, msg_id=%d", msg_id); + break; + case MQTT_EVENT_DISCONNECTED: + if(lvgl_port_lock(0)){ + ESP_LOGE(TAG,"Statut mqttStatus 0"); + lv_subject_set_int(&mqttStatus,0); + lvgl_port_unlock(); + } + ESP_LOGI(TAG, "MQTT_EVENT_DISCONNECTED"); + break; + + case MQTT_EVENT_SUBSCRIBED: + ESP_LOGI(TAG, "MQTT_EVENT_SUBSCRIBED, msg_id=%d", event->msg_id); + //msg_id = esp_mqtt_client_publish(client, "/topic/qos0", "data", 0, 0, 0); + //ESP_LOGI(TAG, "sent publish successful, msg_id=%d", msg_id); + break; + case MQTT_EVENT_UNSUBSCRIBED: + ESP_LOGI(TAG, "MQTT_EVENT_UNSUBSCRIBED, msg_id=%d", event->msg_id); + break; + case MQTT_EVENT_PUBLISHED: + ESP_LOGI(TAG, "MQTT_EVENT_PUBLISHED, msg_id=%d", event->msg_id); + break; + case MQTT_EVENT_DATA: + lv_subject_set_int(&mqttStatus,2); + ESP_LOGD(TAG, "\nMQTT_EVENT_DATA"); + ESP_LOGD(TAG, "TOPIC=%.*s\n", event->topic_len, event->topic); + ESP_LOGD(TAG, "DATA=%.*s\n", event->data_len, event->data); + if (strncmp(event->topic, topicTempExt, 27) == 0) + { + lvgl_port_lock(0); + // on retransforme en float pour ne garder que la partie entiere de la température + float temp = strtof(event->data, NULL); + char buff[5]; + sprintf(buff,"%.1f",temp); + lv_subject_copy_string(&tempExtSubj, buff); + lvgl_port_unlock(); + } + else if (strncmp(event->topic, topicTempInt, 27) == 0) + { + lvgl_port_lock(0); + // on retransforme en float pour ne garder que la partie entiere de la température + float temp = strtof(event->data, NULL); + char buff[5]; + sprintf(buff,"%.1f",temp); + lv_subject_copy_string(&tempIntSubj, buff); + lvgl_port_unlock(); + } + else if (strncmp(event->topic, topicHauteurCuveEvol, 22) == 0) + { + /* float datas[4] = {}; + splitIt(event->data, event->data_len, datas); + ser1->y_points[0] = 130 - (int)datas[0]; + ser1->y_points[1] = 130 - (int)datas[1]; + ser1->y_points[2] = 130 - (int)datas[2]; + ser1->y_points[3] = 130 - (int)datas[3]; + lvgl_port_lock(0); + lv_chart_refresh(chart); + lvgl_port_unlock(); + */ + + // lv_subject_copy_string(&hauteurCuveEvolSubj, event->data); + } + else if (strncmp(event->topic, topicHauteurCuve, 18) == 0) + { + lvgl_port_lock(0); + char *datas = NULL; + datas = (char *)malloc(event->data_len * sizeof(char)); + stpncpy(datas, event->data, event->data_len); + datas[event->data_len] = '\0'; + lv_subject_copy_string(&hauteurCuveSubj, datas); + free(datas); + lvgl_port_unlock(); + }else if (strncmp(event->topic, topicTest, 4) == 0){ + ESP_LOGD(TAG,"Msg reecu sur test"); + }else if (strncmp(event->topic, topicdomoticCommand, 11) == 0){ + if(strncmp(event->data,"restart",7)==0){ + ESP_LOGI(TAG," Commande 'restart' recue"); + esp_restart(); + } + } + else + { + ESP_LOGE(TAG, "None match :-( %s", event->topic); + } + lv_subject_set_int(&mqttStatus,3); + break; + case MQTT_EVENT_ERROR: + ESP_LOGI(TAG, "MQTT_EVENT_ERROR"); + if (event->error_handle->error_type == MQTT_ERROR_TYPE_TCP_TRANSPORT) + { + log_error_if_nonzero("reported from esp-tls", event->error_handle->esp_tls_last_esp_err); + log_error_if_nonzero("reported from tls stack", event->error_handle->esp_tls_stack_err); + log_error_if_nonzero("captured as transport's socket errno", event->error_handle->esp_transport_sock_errno); + ESP_LOGI(TAG, "Last errno string (%s)", strerror(event->error_handle->esp_transport_sock_errno)); + } + break; + default: + ESP_LOGI(TAG, "Other event id:%d", event->event_id); + break; + } +} +void mqtt_app_start(void) +{ + + lv_subject_init_int(&mqttStatus,-1); + lv_subject_add_observer_obj(&mqttStatus, mqttStatus_obs_cb, NULL, NULL); + + + esp_mqtt_client_config_t mqtt_cfg = { + .broker.address.uri = "mqtt://192.168.0.10", + .network.timeout_ms = 1000}; +#if CONFIG_BROKER_URL_FROM_STDIN + char line[128]; + + if (strcmp(mqtt_cfg.broker.address.uri, "FROM_STDIN") == 0) + { + int count = 0; + printf("Please enter url of mqtt broker\n"); + while (count < 128) + { + int c = fgetc(stdin); + if (c == '\n') + { + line[count] = '\0'; + break; + } + else if (c > 0 && c < 127) + { + line[count] = c; + ++count; + } + vTaskDelay(10 / portTICK_PERIOD_MS); + } + mqtt_cfg.broker.address.uri = line; + printf("Broker url: %s\n", line); + } + else + { + ESP_LOGE(TAG, "Configuration mismatch: wrong broker url"); + abort(); + } +#endif /* CONFIG_BROKER_URL_FROM_STDIN */ + + client = esp_mqtt_client_init(&mqtt_cfg); + /* The last argument may be used to pass data to the event handler, in this example mqtt_event_handler */ + esp_mqtt_client_register_event(client, ESP_EVENT_ANY_ID, mqtt_event_handler, NULL); + esp_mqtt_client_start(client); +} + diff --git a/main/mqtt.h b/main/mqtt.h index 694f675..5e813fa 100644 --- a/main/mqtt.h +++ b/main/mqtt.h @@ -1,3 +1,3 @@ -#pragma once - -void mqtt_app_start(void); +#pragma once + +void mqtt_app_start(void); diff --git a/main/obtain_time.c b/main/obtain_time.c index be65d95..f08788c 100644 --- a/main/obtain_time.c +++ b/main/obtain_time.c @@ -1,32 +1,40 @@ -#include "esp_log.h" -#include "esp_netif_sntp.h" -#include "esp_sntp.h" -#include "obtain_time.h" - -static const char *TAG = "sntp"; - -void time_sync_notification_cb(struct timeval *tv) -{ - ESP_LOGI(TAG, "Notification of a time synchronization event"); -} - -void obtain_time(void) -{ - ESP_LOGI(TAG, "Initializing and starting SNTP"); - esp_sntp_config_t config = ESP_NETIF_SNTP_DEFAULT_CONFIG("pool.ntp.org"); - config.sync_cb = time_sync_notification_cb; // Note: This is only needed if we want - esp_netif_sntp_init(&config); - - // wait for time to be set - time_t now = 0; - struct tm timeinfo = { 0 }; - int retry = 0; - const int retry_count = 15; - while (esp_netif_sntp_sync_wait(2000 / portTICK_PERIOD_MS) == ESP_ERR_TIMEOUT && ++retry < retry_count) { - ESP_LOGI(TAG, "Waiting for system time to be set... (%d/%d)", retry, retry_count); - } - time(&now); - localtime_r(&now, &timeinfo); - - esp_netif_sntp_deinit(); +#include "esp_log.h" +#include "esp_netif_sntp.h" +#include "esp_sntp.h" +#include "obtain_time.h" +#include "esp_lvgl_port.h" + +static const char *TAG = "sntp"; +extern lv_subject_t dateHeureSubj; + +char *days[7]={"Dimanche","Lundi","Mardi","Mercredi","Jeudi","Vendredi","Samedi"}; +char *months[12]={"Janvier","Février","Mars","Avril","Mai","Juin","Juillet","Août","Septembre","Octobre","Novembre","Décembre"}; + +void time_sync_notification_cb(struct timeval *tv) +{ + ESP_LOGI(TAG, "Notification of a time synchronization event"); + //setlocale(LC_ALL, "fr_FR"); + + +} + +void obtain_time(void) +{ + ESP_LOGI(TAG, "Initializing and starting SNTP"); + esp_sntp_config_t config = ESP_NETIF_SNTP_DEFAULT_CONFIG("pool.ntp.org"); + config.sync_cb = time_sync_notification_cb; // Note: This is only needed if we want + esp_netif_sntp_init(&config); + + // wait for time to be set + time_t now = 0; + struct tm timeinfo = { 0 }; + int retry = 0; + const int retry_count = 15; + while (esp_netif_sntp_sync_wait(2000 / portTICK_PERIOD_MS) == ESP_ERR_TIMEOUT && ++retry < retry_count) { + ESP_LOGI(TAG, "Waiting for system time to be set... (%d/%d)", retry, retry_count); + } + time(&now); + localtime_r(&now, &timeinfo); + + esp_netif_sntp_deinit(); } \ No newline at end of file diff --git a/main/obtain_time.h b/main/obtain_time.h index 8e2e6cd..ae4f037 100644 --- a/main/obtain_time.h +++ b/main/obtain_time.h @@ -1,2 +1,2 @@ -void obtain_time(void); -#pragma once +void obtain_time(void); +#pragma once diff --git a/main/wifi.c b/main/wifi.c index 4189b16..4da8f0d 100644 --- a/main/wifi.c +++ b/main/wifi.c @@ -1,185 +1,184 @@ -#include "wifi.h" -#include "esp_wifi.h" -#include "esp_log.h" -#include "esp_lvgl_port.h" - -/* FreeRTOS event group to signal when we are connected*/ -static EventGroupHandle_t s_wifi_event_group; - -/* The event group allows multiple bits for each event, but we only care about two events: - * - we are connected to the AP with an IP - * - we failed to connect after the maximum amount of retries */ -#define WIFI_CONNECTED_BIT BIT0 -#define WIFI_FAIL_BIT BIT1 - -#define EXAMPLE_ESP_WIFI_SSID "wifimms3" -#define EXAMPLE_ESP_WIFI_PASS "mmswifi0611" -#define EXAMPLE_ESP_MAXIMUM_RETRY 5 - -#define ESP_WIFI_SAE_MODE WPA3_SAE_PWE_BOTH -#define EXAMPLE_H2E_IDENTIFIER CONFIG_ESP_WIFI_PW_ID -#define ESP_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA2_PSK - -static const char *TAG = "wifi"; - -static int s_retry_num = 0; - -static lv_subject_t wifiStatus; -LV_IMAGE_DECLARE(wifi_ok); -LV_IMAGE_DECLARE(wifi_ko); - -static void wifiStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject); - - -static void wifiStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject) -{ - ESP_LOGE(TAG, "On passe dans le callback de chgt de statut; %li", lv_subject_get_int(subject)); - lv_obj_t * wifiSt = lv_obj_get_child(lv_obj_get_child(lv_layer_top(), 0),2); - if(lv_obj_check_type(wifiSt, &lv_image_class)){ - switch (lv_subject_get_int(subject)) - { - case 0: - lv_image_set_src(wifiSt,&wifi_ko); - break; - case 1: - lv_image_set_src(wifiSt,&wifi_ok); - break; - default: - break; - } - }else{ - ESP_LOGE(TAG, "L'objet recuip en semble pas etre du bon type"); - } - //int32_t prev_v = lv_subject_get_previous_int(subject); - //int32_t cur_v = lv_subject_get_int(subject); - - //lv_obj_t * btn = lv_observer_get_target(observer); -} - -static void wifi_event_handler(void *arg, esp_event_base_t event_base, int32_t event_id, void *event_data) -{ - if (event_base == WIFI_EVENT && event_id == WIFI_EVENT_STA_START) - { - esp_wifi_connect(); - } - else if (event_base == WIFI_EVENT && event_id == WIFI_EVENT_STA_DISCONNECTED) - { - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut Wifi 0"); - lv_subject_set_int(&wifiStatus,0); - lvgl_port_unlock(); - } - if (s_retry_num < EXAMPLE_ESP_MAXIMUM_RETRY) - { - esp_wifi_connect(); - s_retry_num++; - ESP_LOGI(TAG, "retry to connect to the AP"); - } - else - { - xEventGroupSetBits(s_wifi_event_group, WIFI_FAIL_BIT); - } - ESP_LOGI(TAG, "connect to the AP fail"); - } - else if (event_base == IP_EVENT && event_id == IP_EVENT_STA_GOT_IP) - { - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut Wifi 1"); - lv_subject_set_int(&wifiStatus,1); - lvgl_port_unlock(); - } - ip_event_got_ip_t *event = (ip_event_got_ip_t *)event_data; - ESP_LOGI(TAG, "got ip:" IPSTR, IP2STR(&event->ip_info.ip)); - s_retry_num = 0; - xEventGroupSetBits(s_wifi_event_group, WIFI_CONNECTED_BIT); - } -} -void wifi_init_sta(void) -{ - s_wifi_event_group = xEventGroupCreate(); - - ESP_ERROR_CHECK(esp_netif_init()); - - ESP_ERROR_CHECK(esp_event_loop_create_default()); - esp_netif_create_default_wifi_sta(); - - wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT(); - ESP_ERROR_CHECK(esp_wifi_init(&cfg)); - - esp_event_handler_instance_t instance_any_id; - esp_event_handler_instance_t instance_got_ip; - ESP_ERROR_CHECK(esp_event_handler_instance_register(WIFI_EVENT, - ESP_EVENT_ANY_ID, - &wifi_event_handler, - NULL, - &instance_any_id)); - ESP_ERROR_CHECK(esp_event_handler_instance_register(IP_EVENT, - IP_EVENT_STA_GOT_IP, - &wifi_event_handler, - NULL, - &instance_got_ip)); - - wifi_config_t wifi_config = { - .sta = { - .ssid = EXAMPLE_ESP_WIFI_SSID, - .password = EXAMPLE_ESP_WIFI_PASS, - /* Authmode threshold resets to WPA2 as default if password matches WPA2 standards (pasword len => 8). - * If you want to connect the device to deprecated WEP/WPA networks, Please set the threshold value - * to WIFI_AUTH_WEP/WIFI_AUTH_WPA_PSK and set the password with length and format matching to - * WIFI_AUTH_WEP/WIFI_AUTH_WPA_PSK standards. - */ - .threshold.authmode = ESP_WIFI_SCAN_AUTH_MODE_THRESHOLD, - .sae_pwe_h2e = ESP_WIFI_SAE_MODE, - .sae_h2e_identifier = EXAMPLE_H2E_IDENTIFIER, - }, - }; - ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA)); - ESP_ERROR_CHECK(esp_wifi_set_config(WIFI_IF_STA, &wifi_config)); - ESP_ERROR_CHECK(esp_wifi_start()); - - ESP_LOGI(TAG, "wifi_init_sta finished."); - lv_subject_init_int(&wifiStatus,0); - lv_subject_add_observer_obj(&wifiStatus, wifiStatus_obs_cb, NULL, NULL); - - - /* Waiting until either the connection is established (WIFI_CONNECTED_BIT) or connection failed for the maximum - * number of re-tries (WIFI_FAIL_BIT). The bits are set by event_handler() (see above) */ - EventBits_t bits = xEventGroupWaitBits(s_wifi_event_group, - WIFI_CONNECTED_BIT | WIFI_FAIL_BIT, - pdFALSE, - pdFALSE, - portMAX_DELAY); - - /* xEventGroupWaitBits() returns the bits before the call returned, hence we can test which event actually - * happened. */ - if (bits & WIFI_CONNECTED_BIT) - { - ESP_LOGI(TAG, "connected to ap SSID:%s password:%s", - EXAMPLE_ESP_WIFI_SSID, EXAMPLE_ESP_WIFI_PASS); - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut Wifi 1"); - lv_subject_set_int(&wifiStatus,1); - lvgl_port_unlock(); - } - } - else if (bits & WIFI_FAIL_BIT) - { - ESP_LOGI(TAG, "Failed to connect to SSID:%s, password:%s", - EXAMPLE_ESP_WIFI_SSID, EXAMPLE_ESP_WIFI_PASS); - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut Wifi 0"); - lv_subject_set_int(&wifiStatus,0); - lvgl_port_unlock(); - } - } - else - { - ESP_LOGE(TAG, "UNEXPECTED EVENT"); - if(lvgl_port_lock(0)){ - ESP_LOGE(TAG,"Statut Wifi 0"); - lv_subject_set_int(&wifiStatus,0); - lvgl_port_unlock(); - } - - } -} +#include "wifi.h" +#include "esp_wifi.h" +#include "esp_log.h" +#include "esp_lvgl_port.h" + +/* FreeRTOS event group to signal when we are connected*/ +static EventGroupHandle_t s_wifi_event_group; + +/* The event group allows multiple bits for each event, but we only care about two events: + * - we are connected to the AP with an IP + * - we failed to connect after the maximum amount of retries */ +#define WIFI_CONNECTED_BIT BIT0 +#define WIFI_FAIL_BIT BIT1 + +#define EXAMPLE_ESP_WIFI_SSID "wifimms3" +#define EXAMPLE_ESP_WIFI_PASS "mmswifi0611" +#define EXAMPLE_ESP_MAXIMUM_RETRY 5 + +#define ESP_WIFI_SAE_MODE WPA3_SAE_PWE_BOTH +#define EXAMPLE_H2E_IDENTIFIER CONFIG_ESP_WIFI_PW_ID +#define ESP_WIFI_SCAN_AUTH_MODE_THRESHOLD WIFI_AUTH_WPA2_PSK + +static const char *TAG = "wifi"; + +static int s_retry_num = 0; + +static lv_subject_t wifiStatus; +LV_IMAGE_DECLARE(wifi_ok); +LV_IMAGE_DECLARE(wifi_ko); + +static void wifiStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject); + + +static void wifiStatus_obs_cb(lv_observer_t * observer, lv_subject_t * subject) +{ + ESP_LOGE(TAG, "On passe dans le callback de chgt de statut; %li", lv_subject_get_int(subject)); + lv_obj_t * wifiSt = lv_obj_get_child(lv_obj_get_child(lv_layer_top(), 0),2); + if(lv_obj_check_type(wifiSt, &lv_image_class)){ + switch (lv_subject_get_int(subject)) + { + case 0: + lv_image_set_src(wifiSt,&wifi_ko); + break; + case 1: + lv_image_set_src(wifiSt,&wifi_ok); + break; + default: + break; + } + }else{ + ESP_LOGE(TAG, "L'objet recuip en semble pas etre du bon type"); + } + //int32_t prev_v = lv_subject_get_previous_int(subject); + //int32_t cur_v = lv_subject_get_int(subject); + + //lv_obj_t * btn = lv_observer_get_target(observer); +} + +static void wifi_event_handler(void *arg, esp_event_base_t event_base, int32_t event_id, void *event_data) +{ + if (event_base == WIFI_EVENT && event_id == WIFI_EVENT_STA_START) + { + esp_wifi_connect(); + } + else if (event_base == WIFI_EVENT && event_id == WIFI_EVENT_STA_DISCONNECTED) + { + if(lvgl_port_lock(0)){ + ESP_LOGE(TAG,"Statut Wifi 0"); + lv_subject_set_int(&wifiStatus,0); + lvgl_port_unlock(); + } + if (s_retry_num < EXAMPLE_ESP_MAXIMUM_RETRY) + { + esp_wifi_connect(); + s_retry_num++; + ESP_LOGI(TAG, "retry to connect to the AP"); + } + else + { + xEventGroupSetBits(s_wifi_event_group, WIFI_FAIL_BIT); + } + ESP_LOGI(TAG, "connect to the AP fail"); + } + else if (event_base == IP_EVENT && event_id == IP_EVENT_STA_GOT_IP) + { + if(lvgl_port_lock(0)){ + ESP_LOGE(TAG,"Statut Wifi 1"); + lv_subject_set_int(&wifiStatus,1); + lvgl_port_unlock(); + } + ip_event_got_ip_t *event = (ip_event_got_ip_t *)event_data; + ESP_LOGI(TAG, "got ip:" IPSTR, IP2STR(&event->ip_info.ip)); + s_retry_num = 0; + xEventGroupSetBits(s_wifi_event_group, WIFI_CONNECTED_BIT); + } +} +void wifi_init_sta(void) +{ + s_wifi_event_group = xEventGroupCreate(); + + ESP_ERROR_CHECK(esp_netif_init()); + + ESP_ERROR_CHECK(esp_event_loop_create_default()); + esp_netif_create_default_wifi_sta(); + + wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT(); + ESP_ERROR_CHECK(esp_wifi_init(&cfg)); + + esp_event_handler_instance_t instance_any_id; + esp_event_handler_instance_t instance_got_ip; + ESP_ERROR_CHECK(esp_event_handler_instance_register(WIFI_EVENT, + ESP_EVENT_ANY_ID, + &wifi_event_handler, + NULL, + &instance_any_id)); + ESP_ERROR_CHECK(esp_event_handler_instance_register(IP_EVENT, + IP_EVENT_STA_GOT_IP, + &wifi_event_handler, + NULL, + &instance_got_ip)); + + wifi_config_t wifi_config = { + .sta = { + .ssid = EXAMPLE_ESP_WIFI_SSID, + .password = EXAMPLE_ESP_WIFI_PASS, + /* Authmode threshold resets to WPA2 as default if password matches WPA2 standards (pasword len => 8). + * If you want to connect the device to deprecated WEP/WPA networks, Please set the threshold value + * to WIFI_AUTH_WEP/WIFI_AUTH_WPA_PSK and set the password with length and format matching to + * WIFI_AUTH_WEP/WIFI_AUTH_WPA_PSK standards. + */ + .threshold.authmode = ESP_WIFI_SCAN_AUTH_MODE_THRESHOLD, + .sae_pwe_h2e = ESP_WIFI_SAE_MODE, + .sae_h2e_identifier = EXAMPLE_H2E_IDENTIFIER, + }, + }; + ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA)); + ESP_ERROR_CHECK(esp_wifi_set_config(WIFI_IF_STA, &wifi_config)); + ESP_ERROR_CHECK(esp_wifi_start()); + + ESP_LOGI(TAG, "wifi_init_sta finished."); + lv_subject_init_int(&wifiStatus,0); + lv_subject_add_observer_obj(&wifiStatus, wifiStatus_obs_cb, NULL, NULL); + + + /* Waiting until either the connection is established (WIFI_CONNECTED_BIT) or connection failed for the maximum + * number of re-tries (WIFI_FAIL_BIT). The bits are set by event_handler() (see above) */ + EventBits_t bits = xEventGroupWaitBits(s_wifi_event_group, + WIFI_CONNECTED_BIT | WIFI_FAIL_BIT, + pdFALSE, + pdFALSE, + portMAX_DELAY); + + /* xEventGroupWaitBits() returns the bits before the call returned, hence we can test which event actually + * happened. */ + if (bits & WIFI_CONNECTED_BIT) + { + ESP_LOGI(TAG, "connected to ap SSID:%s", EXAMPLE_ESP_WIFI_SSID); + if(lvgl_port_lock(0)){ + ESP_LOGE(TAG,"Statut Wifi 1"); + lv_subject_set_int(&wifiStatus,1); + lvgl_port_unlock(); + } + } + else if (bits & WIFI_FAIL_BIT) + { + ESP_LOGI(TAG, "Failed to connect to SSID:%s, password:%s", + EXAMPLE_ESP_WIFI_SSID, EXAMPLE_ESP_WIFI_PASS); + if(lvgl_port_lock(0)){ + ESP_LOGE(TAG,"Statut Wifi 0"); + lv_subject_set_int(&wifiStatus,0); + lvgl_port_unlock(); + } + } + else + { + ESP_LOGE(TAG, "UNEXPECTED EVENT"); + if(lvgl_port_lock(0)){ + ESP_LOGE(TAG,"Statut Wifi 0"); + lv_subject_set_int(&wifiStatus,0); + lvgl_port_unlock(); + } + + } +} diff --git a/main/wifi.h b/main/wifi.h index 072517d..d992b86 100644 --- a/main/wifi.h +++ b/main/wifi.h @@ -1,2 +1,2 @@ -#pragma once +#pragma once void wifi_init_sta(void); \ No newline at end of file diff --git a/p2j.png b/p2j.png new file mode 100644 index 0000000..fe0add7 Binary files /dev/null and b/p2j.png differ diff --git a/main/images/p2j.svg b/p2j.svg similarity index 100% rename from main/images/p2j.svg rename to p2j.svg diff --git a/p2n.png b/p2n.png new file mode 100644 index 0000000..48ceeb8 Binary files /dev/null and b/p2n.png differ diff --git a/main/images/p2n.svg b/p2n.svg similarity index 100% rename from main/images/p2n.svg rename to p2n.svg diff --git a/p6bisj.png b/p6bisj.png new file mode 100644 index 0000000..246da99 Binary files /dev/null and b/p6bisj.png differ diff --git a/p6bisj.svg b/p6bisj.svg new file mode 100644 index 0000000..55543f7 --- /dev/null +++ b/p6bisj.svg @@ -0,0 +1,22 @@ + + + + +10Plan de travail 1 + + + + + + + diff --git a/partition_table/partitionTable.csv b/partition_table/partitionTable.csv index 852aebf..ca65f56 100644 --- a/partition_table/partitionTable.csv +++ b/partition_table/partitionTable.csv @@ -1,9 +1,9 @@ -# ESP-IDF Partition Table -# Name, Type, SubType, Offset, Size, Flags -nvs,data,nvs,0x9000,24K, -otadata,data,ota,0xf000,8K, -phy_init,data,phy,0x11000,4K, -factory,app,factory,0x20000,3M, -ota_0,app,ota_0,0x320000,3M, -ota_1,app,ota_1,0x620000,3M, -littlefs,data,littlefs,0x920000,1M, +# ESP-IDF Partition Table +# Name, Type, SubType, Offset, Size, Flags +nvs,data,nvs,0x9000,24K, +otadata,data,ota,0xf000,8K, +phy_init,data,phy,0x11000,4K, +factory,app,factory,0x20000,3M, +ota_0,app,ota_0,0x320000,3M, +ota_1,app,ota_1,0x620000,3M, +littlefs,data,littlefs,0x920000,1M, diff --git a/partitions copy.csv b/partitions copy.csv index 111c125..938c8d8 100644 --- a/partitions copy.csv +++ b/partitions copy.csv @@ -1,5 +1,5 @@ -# Name, Type, SubType, Offset, Size, Flags -# Note: if you change the phy_init or app partition offset, make sure to change the offset in Kconfig.projbuild -nvs, data, nvs, 0x9000, 0x6000, -phy_init, data, phy, 0xf000, 0x1000, -factory, app, factory, 0x10000, 3M, +# Name, Type, SubType, Offset, Size, Flags +# Note: if you change the phy_init or app partition offset, make sure to change the offset in Kconfig.projbuild +nvs, data, nvs, 0x9000, 0x6000, +phy_init, data, phy, 0xf000, 0x1000, +factory, app, factory, 0x10000, 3M, diff --git a/pytest_simple_ota.py b/pytest_simple_ota.py new file mode 100644 index 0000000..28ee0eb --- /dev/null +++ b/pytest_simple_ota.py @@ -0,0 +1,378 @@ +# SPDX-FileCopyrightText: 2022-2024 Espressif Systems (Shanghai) CO LTD +# SPDX-License-Identifier: Unlicense OR CC0-1.0 +import http.server +import multiprocessing +import os +import ssl +import subprocess +import sys +from typing import Any +from typing import Optional +from typing import Tuple + +import pexpect +import pytest +from pytest_embedded import Dut + +try: + from common_test_methods import get_env_config_variable, get_host_ip4_by_dest_ip +except ModuleNotFoundError: + idf_path = os.environ['IDF_PATH'] + sys.path.insert(0, idf_path + '/tools/ci/python_packages') + from common_test_methods import get_env_config_variable, get_host_ip4_by_dest_ip + +server_cert = '-----BEGIN CERTIFICATE-----\n' \ + 'MIIDWDCCAkACCQCbF4+gVh/MLjANBgkqhkiG9w0BAQsFADBuMQswCQYDVQQGEwJJ\n'\ + 'TjELMAkGA1UECAwCTUgxDDAKBgNVBAcMA1BVTjEMMAoGA1UECgwDRVNQMQwwCgYD\n'\ + 'VQQLDANFU1AxDDAKBgNVBAMMA0VTUDEaMBgGCSqGSIb3DQEJARYLZXNwQGVzcC5j\n'\ + 'b20wHhcNMjEwNzEyMTIzNjI3WhcNNDEwNzA3MTIzNjI3WjBuMQswCQYDVQQGEwJJ\n'\ + 'TjELMAkGA1UECAwCTUgxDDAKBgNVBAcMA1BVTjEMMAoGA1UECgwDRVNQMQwwCgYD\n'\ + 'VQQLDANFU1AxDDAKBgNVBAMMA0VTUDEaMBgGCSqGSIb3DQEJARYLZXNwQGVzcC5j\n'\ + 'b20wggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDhxF/y7bygndxPwiWL\n'\ + 'SwS9LY3uBMaJgup0ufNKVhx+FhGQOu44SghuJAaH3KkPUnt6SOM8jC97/yQuc32W\n'\ + 'ukI7eBZoA12kargSnzdv5m5rZZpd+NznSSpoDArOAONKVlzr25A1+aZbix2mKRbQ\n'\ + 'S5w9o1N2BriQuSzd8gL0Y0zEk3VkOWXEL+0yFUT144HnErnD+xnJtHe11yPO2fEz\n'\ + 'YaGiilh0ddL26PXTugXMZN/8fRVHP50P2OG0SvFpC7vghlLp4VFM1/r3UJnvL6Oz\n'\ + '3ALc6dhxZEKQucqlpj8l1UegszQToopemtIj0qXTHw2+uUnkUyWIPjPC+wdOAoap\n'\ + 'rFTRAgMBAAEwDQYJKoZIhvcNAQELBQADggEBAItw24y565k3C/zENZlxyzto44ud\n'\ + 'IYPQXN8Fa2pBlLe1zlSIyuaA/rWQ+i1daS8nPotkCbWZyf5N8DYaTE4B0OfvoUPk\n'\ + 'B5uGDmbuk6akvlB5BGiYLfQjWHRsK9/4xjtIqN1H58yf3QNROuKsPAeywWS3Fn32\n'\ + '3//OpbWaClQePx6udRYMqAitKR+QxL7/BKZQsX+UyShuq8hjphvXvk0BW8ONzuw9\n'\ + 'RcoORxM0FzySYjeQvm4LhzC/P3ZBhEq0xs55aL2a76SJhq5hJy7T/Xz6NFByvlrN\n'\ + 'lFJJey33KFrAf5vnV9qcyWFIo7PYy2VsaaEjFeefr7q3sTFSMlJeadexW2Y=\n'\ + '-----END CERTIFICATE-----\n' + +server_key = '-----BEGIN PRIVATE KEY-----\n'\ + 'MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQDhxF/y7bygndxP\n'\ + 'wiWLSwS9LY3uBMaJgup0ufNKVhx+FhGQOu44SghuJAaH3KkPUnt6SOM8jC97/yQu\n'\ + 'c32WukI7eBZoA12kargSnzdv5m5rZZpd+NznSSpoDArOAONKVlzr25A1+aZbix2m\n'\ + 'KRbQS5w9o1N2BriQuSzd8gL0Y0zEk3VkOWXEL+0yFUT144HnErnD+xnJtHe11yPO\n'\ + '2fEzYaGiilh0ddL26PXTugXMZN/8fRVHP50P2OG0SvFpC7vghlLp4VFM1/r3UJnv\n'\ + 'L6Oz3ALc6dhxZEKQucqlpj8l1UegszQToopemtIj0qXTHw2+uUnkUyWIPjPC+wdO\n'\ + 'AoaprFTRAgMBAAECggEAE0HCxV/N1Q1h+1OeDDGL5+74yjKSFKyb/vTVcaPCrmaH\n'\ + 'fPvp0ddOvMZJ4FDMAsiQS6/n4gQ7EKKEnYmwTqj4eUYW8yxGUn3f0YbPHbZT+Mkj\n'\ + 'z5woi3nMKi/MxCGDQZX4Ow3xUQlITUqibsfWcFHis8c4mTqdh4qj7xJzehD2PVYF\n'\ + 'gNHZsvVj6MltjBDAVwV1IlGoHjuElm6vuzkfX7phxcA1B4ZqdYY17yCXUnvui46z\n'\ + 'Xn2kUTOOUCEgfgvGa9E+l4OtdXi5IxjaSraU+dlg2KsE4TpCuN2MEVkeR5Ms3Y7Q\n'\ + 'jgJl8vlNFJDQpbFukLcYwG7rO5N5dQ6WWfVia/5XgQKBgQD74at/bXAPrh9NxPmz\n'\ + 'i1oqCHMDoM9sz8xIMZLF9YVu3Jf8ux4xVpRSnNy5RU1gl7ZXbpdgeIQ4v04zy5aw\n'\ + '8T4tu9K3XnR3UXOy25AK0q+cnnxZg3kFQm+PhtOCKEFjPHrgo2MUfnj+EDddod7N\n'\ + 'JQr9q5rEFbqHupFPpWlqCa3QmQKBgQDldWUGokNaEpmgHDMnHxiibXV5LQhzf8Rq\n'\ + 'gJIQXb7R9EsTSXEvsDyqTBb7PHp2Ko7rZ5YQfyf8OogGGjGElnPoU/a+Jij1gVFv\n'\ + 'kZ064uXAAISBkwHdcuobqc5EbG3ceyH46F+FBFhqM8KcbxJxx08objmh58+83InN\n'\ + 'P9Qr25Xw+QKBgEGXMHuMWgQbSZeM1aFFhoMvlBO7yogBTKb4Ecpu9wI5e3Kan3Al\n'\ + 'pZYltuyf+VhP6XG3IMBEYdoNJyYhu+nzyEdMg8CwXg+8LC7FMis/Ve+o7aS5scgG\n'\ + '1to/N9DK/swCsdTRdzmc/ZDbVC+TuVsebFBGYZTyO5KgqLpezqaIQrTxAoGALFCU\n'\ + '10glO9MVyl9H3clap5v+MQ3qcOv/EhaMnw6L2N6WVT481tnxjW4ujgzrFcE4YuxZ\n'\ + 'hgwYu9TOCmeqopGwBvGYWLbj+C4mfSahOAs0FfXDoYazuIIGBpuv03UhbpB1Si4O\n'\ + 'rJDfRnuCnVWyOTkl54gKJ2OusinhjztBjcrV1XkCgYEA3qNi4uBsPdyz9BZGb/3G\n'\ + 'rOMSw0CaT4pEMTLZqURmDP/0hxvTk1polP7O/FYwxVuJnBb6mzDa0xpLFPTpIAnJ\n'\ + 'YXB8xpXU69QVh+EBbemdJWOd+zp5UCfXvb2shAeG3Tn/Dz4cBBMEUutbzP+or0nG\n'\ + 'vSXnRLaxQhooWm+IuX9SuBQ=\n'\ + '-----END PRIVATE KEY-----\n' + +OTA_0_ADDRESS = '0x20000' +OTA_1_ADDRESS = '0x1d0000' + + +def start_https_server(ota_image_dir: str, server_ip: str, server_port: int, server_file: Optional[str] = None, key_file: Optional[str] = None) -> None: + os.chdir(ota_image_dir) + + if server_file is None: + server_file = os.path.join(ota_image_dir, 'server_cert.pem') + cert_file_handle = open(server_file, 'w+') + cert_file_handle.write(server_cert) + cert_file_handle.close() + + if key_file is None: + key_file = os.path.join(ota_image_dir, 'server_key.pem') + key_file_handle = open('server_key.pem', 'w+') + key_file_handle.write(server_key) + key_file_handle.close() + + httpd = http.server.HTTPServer((server_ip, server_port), http.server.SimpleHTTPRequestHandler) + + ssl_context = ssl.SSLContext(ssl.PROTOCOL_TLS_SERVER) + ssl_context.load_cert_chain(certfile=server_file, keyfile=key_file) + + httpd.socket = ssl_context.wrap_socket(httpd.socket, server_side=True) + httpd.serve_forever() + + +def start_tls1_3_server(ota_image_dir: str, server_port: int) -> subprocess.Popen: + os.chdir(ota_image_dir) + server_file = os.path.join(ota_image_dir, 'server_cert.pem') + cert_file_handle = open(server_file, 'w+') + cert_file_handle.write(server_cert) + cert_file_handle.close() + + key_file = os.path.join(ota_image_dir, 'server_key.pem') + key_file_handle = open('server_key.pem', 'w+') + key_file_handle.write(server_key) + key_file_handle.close() + + chunked_server = subprocess.Popen(['openssl', 's_server', '-tls1_3', '-WWW', '-key', key_file, '-cert', server_file, '-port', str(server_port)]) + return chunked_server + + +def check_sha256(sha256_expected: str, sha256_reported: str) -> None: + print('sha256_expected: %s' % (sha256_expected)) + print('sha256_reported: %s' % (sha256_reported)) + if sha256_expected not in sha256_reported: + raise ValueError('SHA256 mismatch') + else: + print('SHA256 expected and reported are the same') + + +def calc_all_sha256(dut: Dut) -> Tuple[str, str]: + bootloader_path = os.path.join(dut.app.binary_path, 'bootloader', 'bootloader.bin') + sha256_bootloader = dut.app.get_sha256(bootloader_path) + + app_path = os.path.join(dut.app.binary_path, 'simple_ota.bin') + sha256_app = dut.app.get_sha256(app_path) + + return str(sha256_bootloader), str(sha256_app) + + +def setting_connection(dut: Dut, env_name: Optional[str] = None) -> Any: + if env_name is not None and dut.app.sdkconfig.get('EXAMPLE_WIFI_SSID_PWD_FROM_STDIN') is True: + dut.expect('Please input ssid password:') + ap_ssid = get_env_config_variable(env_name, 'ap_ssid') + ap_password = get_env_config_variable(env_name, 'ap_password') + dut.write(f'{ap_ssid} {ap_password}') + try: + ip_address = dut.expect(r'IPv4 address: (\d+\.\d+\.\d+\.\d+)[^\d]', timeout=30)[1].decode() + print(f'Connected to AP/Ethernet with IP: {ip_address}') + except pexpect.exceptions.TIMEOUT: + raise ValueError('ENV_TEST_FAILURE: Cannot connect to AP/Ethernet') + return get_host_ip4_by_dest_ip(ip_address) + + +@pytest.mark.esp32 +@pytest.mark.esp32c3 +@pytest.mark.esp32s3 +@pytest.mark.wifi_high_traffic +def test_examples_protocol_simple_ota_example(dut: Dut) -> None: + """ + steps: | + 1. join AP/Ethernet + 2. Fetch OTA image over HTTPS + 3. Reboot with the new OTA image + """ + sha256_bootloader, sha256_app = calc_all_sha256(dut) + # Start server + thread1 = multiprocessing.Process(target=start_https_server, args=(dut.app.binary_path, '0.0.0.0', 8000)) + thread1.daemon = True + thread1.start() + try: + # start test + dut.expect(f'Loaded app from partition at offset {OTA_0_ADDRESS}', timeout=30) + check_sha256(sha256_bootloader, str(dut.expect(r'SHA-256 for bootloader:\s+([a-f0-9]){64}')[0])) + check_sha256(sha256_app, str(dut.expect(r'SHA-256 for current firmware:\s+([a-f0-9]){64}')[0])) + # Parse IP address of STA + env_name = 'wifi_high_traffic' if dut.app.sdkconfig.get('EXAMPLE_WIFI_SSID_PWD_FROM_STDIN') is True else None + host_ip = setting_connection(dut, env_name) + dut.expect('Starting OTA example task', timeout=30) + print(f'writing to device: https://{host_ip}:8000/simple_ota.bin') + dut.write(f'https://{host_ip}:8000/simple_ota.bin') + dut.expect('OTA Succeed, Rebooting...', timeout=60) + # after reboot + dut.expect(f'Loaded app from partition at offset {OTA_1_ADDRESS}', timeout=30) + dut.expect('OTA example app_main start', timeout=10) + finally: + thread1.terminate() + + +@pytest.mark.esp32 +@pytest.mark.ethernet_ota +@pytest.mark.parametrize('config', ['spiram',], indirect=True) +def test_examples_protocol_simple_ota_example_ethernet_with_spiram_config(dut: Dut) -> None: + """ + steps: | + 1. join AP/Ethernet + 2. Fetch OTA image over HTTPS + 3. Reboot with the new OTA image + """ + # Start server + thread1 = multiprocessing.Process(target=start_https_server, args=(dut.app.binary_path, '0.0.0.0', 8000)) + thread1.daemon = True + thread1.start() + try: + # start test + dut.expect(f'Loaded app from partition at offset {OTA_0_ADDRESS}', timeout=30) + host_ip = setting_connection(dut) + dut.expect('Starting OTA example task', timeout=30) + print(f'writing to device: https://{host_ip}:8000/simple_ota.bin') + dut.write(f'https://{host_ip}:8000/simple_ota.bin') + dut.expect('OTA Succeed, Rebooting...', timeout=60) + # after reboot + dut.expect(f'Loaded app from partition at offset {OTA_1_ADDRESS}', timeout=30) + dut.expect('OTA example app_main start', timeout=10) + finally: + thread1.terminate() + + +@pytest.mark.esp32 +@pytest.mark.esp32c3 +@pytest.mark.flash_encryption_wifi_high_traffic +@pytest.mark.nightly_run +@pytest.mark.parametrize('config', ['flash_enc_wifi',], indirect=True) +@pytest.mark.parametrize('skip_autoflash', ['y'], indirect=True) +def test_examples_protocol_simple_ota_example_with_flash_encryption_wifi(dut: Dut) -> None: + """ + steps: | + 1. join AP/Ethernet + 2. Fetch OTA image over HTTPS + 3. Reboot with the new OTA image + """ + # CONFIG_PARTITION_TABLE_TWO_OTA_ENCRYPTED_NVS==y, it includes partitions_two_ota_encr_nvs.csv + FACTORY_ADDRESS = '0x20000' + OTA_0_ADDRESS = '0x120000' + # OTA_1_ADDRESS = '0x220000' + + # start test + # Erase flash + dut.serial.erase_flash() + dut.serial.flash() + # Start server + thread1 = multiprocessing.Process(target=start_https_server, args=(dut.app.binary_path, '0.0.0.0', 8000)) + thread1.daemon = True + thread1.start() + try: + dut.expect(f'Loaded app from partition at offset {FACTORY_ADDRESS}', timeout=30) + dut.expect('Flash encryption mode is DEVELOPMENT', timeout=10) + # Parse IP address of STA + env_name = 'flash_encryption_wifi_high_traffic' if dut.app.sdkconfig.get('EXAMPLE_WIFI_SSID_PWD_FROM_STDIN') is True else None + host_ip = setting_connection(dut, env_name) + + dut.expect('Starting OTA example task', timeout=30) + print(f'writing to device: https://{host_ip}:8000/simple_ota.bin') + dut.write(f'https://{host_ip}:8000/simple_ota.bin') + dut.expect('OTA Succeed, Rebooting...', timeout=60) + # after reboot + dut.expect(f'Loaded app from partition at offset {OTA_0_ADDRESS}', timeout=30) + dut.expect('Flash encryption mode is DEVELOPMENT', timeout=10) + dut.expect('OTA example app_main start', timeout=10) + finally: + thread1.terminate() + + +@pytest.mark.esp32 +@pytest.mark.ethernet_ota +@pytest.mark.parametrize('config', ['on_update_no_sb_ecdsa',], indirect=True) +def test_examples_protocol_simple_ota_example_with_verify_app_signature_on_update_no_secure_boot_ecdsa(dut: Dut) -> None: + """ + steps: | + 1. join AP/Ethernet + 2. Fetch OTA image over HTTPS + 3. Reboot with the new OTA image + """ + sha256_bootloader, sha256_app = calc_all_sha256(dut) + # Start server + thread1 = multiprocessing.Process(target=start_https_server, args=(dut.app.binary_path, '0.0.0.0', 8000)) + thread1.daemon = True + thread1.start() + try: + # start test + dut.expect(f'Loaded app from partition at offset {OTA_0_ADDRESS}', timeout=30) + check_sha256(sha256_bootloader, str(dut.expect(r'SHA-256 for bootloader:\s+([a-f0-9]){64}')[0])) + check_sha256(sha256_app, str(dut.expect(r'SHA-256 for current firmware:\s+([a-f0-9]){64}')[0])) + + host_ip = setting_connection(dut) + + dut.expect('Starting OTA example task', timeout=30) + print(f'writing to device: https://{host_ip}:8000/simple_ota.bin') + dut.write(f'https://{host_ip}:8000/simple_ota.bin') + dut.expect(f'Writing to partition at offset {OTA_1_ADDRESS}', timeout=20) + dut.expect('Verifying image signature...', timeout=60) + dut.expect('OTA Succeed, Rebooting...', timeout=60) + # after reboot + dut.expect(f'Loaded app from partition at offset {OTA_1_ADDRESS}', timeout=20) + dut.expect('OTA example app_main start', timeout=10) + finally: + thread1.terminate() + + +@pytest.mark.esp32 +@pytest.mark.ethernet_ota +@pytest.mark.parametrize('config', ['on_update_no_sb_rsa',], indirect=True) +def test_examples_protocol_simple_ota_example_with_verify_app_signature_on_update_no_secure_boot_rsa(dut: Dut) -> None: + """ + steps: | + 1. join AP/Ethernet + 2. Fetch OTA image over HTTPS + 3. Reboot with the new OTA image + """ + sha256_bootloader, sha256_app = calc_all_sha256(dut) + # Start server + thread1 = multiprocessing.Process(target=start_https_server, args=(dut.app.binary_path, '0.0.0.0', 8000)) + thread1.daemon = True + thread1.start() + try: + # start test + dut.expect(f'Loaded app from partition at offset {OTA_0_ADDRESS}', timeout=30) + check_sha256(sha256_bootloader, str(dut.expect(r'SHA-256 for bootloader:\s+([a-f0-9]){64}')[0])) + check_sha256(sha256_app, str(dut.expect(r'SHA-256 for current firmware:\s+([a-f0-9]){64}')[0])) + + host_ip = setting_connection(dut) + + dut.expect('Starting OTA example task', timeout=30) + print(f'writing to device: https://{host_ip}:8000/simple_ota.bin') + dut.write(f'https://{host_ip}:8000/simple_ota.bin') + dut.expect(f'Writing to partition at offset {OTA_1_ADDRESS}', timeout=20) + dut.expect('Verifying image signature...', timeout=60) + dut.expect('#0 app key digest == #0 trusted key digest', timeout=10) + dut.expect('Verifying with RSA-PSS...', timeout=10) + dut.expect('Signature verified successfully!', timeout=10) + dut.expect('OTA Succeed, Rebooting...', timeout=60) + # after reboot + dut.expect(f'Loaded app from partition at offset {OTA_1_ADDRESS}', timeout=20) + dut.expect('OTA example app_main start', timeout=10) + finally: + thread1.terminate() + + +@pytest.mark.esp32 +@pytest.mark.ethernet_ota +@pytest.mark.parametrize('config', ['tls1_3',], indirect=True) +def test_examples_protocol_simple_ota_example_tls1_3(dut: Dut) -> None: + """ + steps: | + 1. join AP/Ethernet + 2. Fetch OTA image over HTTPS + 3. Reboot with the new OTA image + """ + sha256_bootloader, sha256_app = calc_all_sha256(dut) + # Start server + tls1_3_server = start_tls1_3_server(dut.app.binary_path, 8000) + try: + # start test + dut.expect(f'Loaded app from partition at offset {OTA_0_ADDRESS}', timeout=30) + check_sha256(sha256_bootloader, str(dut.expect(r'SHA-256 for bootloader:\s+([a-f0-9]){64}')[0])) + check_sha256(sha256_app, str(dut.expect(r'SHA-256 for current firmware:\s+([a-f0-9]){64}')[0])) + # Parse IP address of STA + env_name = 'wifi_high_traffic' if dut.app.sdkconfig.get('EXAMPLE_WIFI_SSID_PWD_FROM_STDIN') is True else None + host_ip = setting_connection(dut, env_name) + + dut.expect('Starting OTA example task', timeout=30) + print(f'writing to device: https://{host_ip}:8000/simple_ota.bin') + dut.write(f'https://{host_ip}:8000/simple_ota.bin') + dut.expect('OTA Succeed, Rebooting...', timeout=120) + # after reboot + dut.expect(f'Loaded app from partition at offset {OTA_1_ADDRESS}', timeout=30) + dut.expect('OTA example app_main start', timeout=10) + finally: + tls1_3_server.kill() + + +if __name__ == '__main__': + if sys.argv[2:]: # if two or more arguments provided: + # Usage: pytest_simple_ota.py [cert_dir] + this_dir = os.path.dirname(os.path.realpath(__file__)) + bin_dir = os.path.join(this_dir, sys.argv[1]) + port = int(sys.argv[2]) + cert_dir = bin_dir if not sys.argv[3:] else os.path.join(this_dir, sys.argv[3]) # optional argument + print(f'Starting HTTPS server at "https://0.0.0.0:{port}"') + start_https_server(bin_dir, '', port, + server_file=os.path.join(cert_dir, 'ca_cert.pem'), + key_file=os.path.join(cert_dir, 'ca_key.pem')) diff --git a/sdkconfig b/sdkconfig index 33b9e7b..2ba1412 100644 --- a/sdkconfig +++ b/sdkconfig @@ -548,6 +548,49 @@ CONFIG_ESP_WIFI_AUTH_WPA2_PSK=y # CONFIG_ESP_WIFI_AUTH_WAPI_PSK is not set # end of Example Configuration +# +# Example Connection Configuration +# +CONFIG_ENV_GPIO_RANGE_MIN=0 +CONFIG_ENV_GPIO_RANGE_MAX=48 +CONFIG_ENV_GPIO_IN_RANGE_MAX=48 +CONFIG_ENV_GPIO_OUT_RANGE_MAX=48 +CONFIG_EXAMPLE_CONNECT_WIFI=y +# CONFIG_EXAMPLE_WIFI_SSID_PWD_FROM_STDIN is not set +CONFIG_EXAMPLE_PROVIDE_WIFI_CONSOLE_CMD=y +CONFIG_EXAMPLE_WIFI_SSID="myssid" +CONFIG_EXAMPLE_WIFI_PASSWORD="mypassword" +CONFIG_EXAMPLE_WIFI_CONN_MAX_RETRY=6 +# CONFIG_EXAMPLE_WIFI_SCAN_METHOD_FAST is not set +CONFIG_EXAMPLE_WIFI_SCAN_METHOD_ALL_CHANNEL=y + +# +# WiFi Scan threshold +# +CONFIG_EXAMPLE_WIFI_SCAN_RSSI_THRESHOLD=-127 +CONFIG_EXAMPLE_WIFI_AUTH_OPEN=y +# CONFIG_EXAMPLE_WIFI_AUTH_WEP is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA2_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA_WPA2_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA2_ENTERPRISE is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA3_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA2_WPA3_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WAPI_PSK is not set +# end of WiFi Scan threshold + +CONFIG_EXAMPLE_WIFI_CONNECT_AP_BY_SIGNAL=y +# CONFIG_EXAMPLE_WIFI_CONNECT_AP_BY_SECURITY is not set +# CONFIG_EXAMPLE_CONNECT_ETHERNET is not set +# CONFIG_EXAMPLE_CONNECT_PPP is not set +CONFIG_EXAMPLE_CONNECT_IPV4=y +CONFIG_EXAMPLE_CONNECT_IPV6=y +CONFIG_EXAMPLE_CONNECT_IPV6_PREF_LOCAL_LINK=y +# CONFIG_EXAMPLE_CONNECT_IPV6_PREF_GLOBAL is not set +# CONFIG_EXAMPLE_CONNECT_IPV6_PREF_SITE_LOCAL is not set +# CONFIG_EXAMPLE_CONNECT_IPV6_PREF_UNIQUE_LOCAL is not set +# end of Example Connection Configuration + # # Compiler options # @@ -582,6 +625,12 @@ CONFIG_COMPILER_ORPHAN_SECTIONS_PLACE=y # Component config # +# +# Console Library +# +# CONFIG_CONSOLE_SORTED_HELP is not set +# end of Console Library + # # Driver Configurations # @@ -776,6 +825,18 @@ CONFIG_SPI_SLAVE_ISR_IN_IRAM=y CONFIG_USJ_ENABLE_USB_SERIAL_JTAG=y # end of ESP-Driver:USB Serial/JTAG Configuration +# +# Ethernet +# +CONFIG_ETH_ENABLED=y +CONFIG_ETH_USE_SPI_ETHERNET=y +# CONFIG_ETH_SPI_ETHERNET_DM9051 is not set +# CONFIG_ETH_SPI_ETHERNET_W5500 is not set +# CONFIG_ETH_SPI_ETHERNET_KSZ8851SNL is not set +# CONFIG_ETH_USE_OPENETH is not set +# CONFIG_ETH_TRANSMIT_MUTEX is not set +# end of Ethernet + # # Event Loop Library # @@ -787,12 +848,19 @@ CONFIG_ESP_EVENT_POST_FROM_IRAM_ISR=y # # ESP HTTP client # -# CONFIG_ESP_HTTP_CLIENT_ENABLE_HTTPS is not set +CONFIG_ESP_HTTP_CLIENT_ENABLE_HTTPS=y # CONFIG_ESP_HTTP_CLIENT_ENABLE_BASIC_AUTH is not set # CONFIG_ESP_HTTP_CLIENT_ENABLE_DIGEST_AUTH is not set # CONFIG_ESP_HTTP_CLIENT_ENABLE_CUSTOM_TRANSPORT is not set # end of ESP HTTP client +# +# ESP HTTPS OTA +# +# CONFIG_ESP_HTTPS_OTA_DECRYPT_CB is not set +# CONFIG_ESP_HTTPS_OTA_ALLOW_HTTP is not set +# end of ESP HTTPS OTA + # # Hardware Settings # @@ -1324,14 +1392,14 @@ CONFIG_LOG_DEFAULT_LEVEL_INFO=y # CONFIG_LOG_DEFAULT_LEVEL_DEBUG is not set # CONFIG_LOG_DEFAULT_LEVEL_VERBOSE is not set CONFIG_LOG_DEFAULT_LEVEL=3 -CONFIG_LOG_MAXIMUM_EQUALS_DEFAULT=y -# CONFIG_LOG_MAXIMUM_LEVEL_DEBUG is not set +# CONFIG_LOG_MAXIMUM_EQUALS_DEFAULT is not set +CONFIG_LOG_MAXIMUM_LEVEL_DEBUG=y # CONFIG_LOG_MAXIMUM_LEVEL_VERBOSE is not set -CONFIG_LOG_MAXIMUM_LEVEL=3 +CONFIG_LOG_MAXIMUM_LEVEL=4 # CONFIG_LOG_MASTER_LEVEL is not set CONFIG_LOG_COLORS=y -CONFIG_LOG_TIMESTAMP_SOURCE_RTOS=y -# CONFIG_LOG_TIMESTAMP_SOURCE_SYSTEM is not set +# CONFIG_LOG_TIMESTAMP_SOURCE_RTOS is not set +CONFIG_LOG_TIMESTAMP_SOURCE_SYSTEM=y # end of Log output # @@ -1822,6 +1890,19 @@ CONFIG_WL_SECTOR_SIZE_4096=y CONFIG_WL_SECTOR_SIZE=4096 # end of Wear Levelling +# +# WiFi Logger configuration +# +# CONFIG_TRANSPORT_PROTOCOL_UDP is not set +CONFIG_TRANSPORT_PROTOCOL_TCP=y +# CONFIG_TRANSPORT_PROTOCOL_WEBSOCKET is not set +CONFIG_ROUTE_ESP_IDF_API_LOGS_TO_WIFI=y +CONFIG_SERVER_IP_ADDRESS="192.168.0.28" +CONFIG_SERVER_PORT=9999 +CONFIG_MESSAGE_QUEUE_SIZE=1000 +CONFIG_BUFFER_SIZE=512 +# end of WiFi Logger configuration + # # ESP LCD TOUCH # @@ -1829,6 +1910,12 @@ CONFIG_ESP_LCD_TOUCH_MAX_POINTS=1 CONFIG_ESP_LCD_TOUCH_MAX_BUTTONS=1 # end of ESP LCD TOUCH +# +# ESP WebSocket client +# +# CONFIG_ESP_WS_CLIENT_ENABLE_DYNAMIC_BUFFER is not set +# end of ESP WebSocket client + # # LittleFS # @@ -2290,6 +2377,7 @@ CONFIG_STACK_CHECK_NONE=y # CONFIG_EVENT_LOOP_PROFILING is not set CONFIG_POST_EVENTS_FROM_ISR=y CONFIG_POST_EVENTS_FROM_IRAM_ISR=y +# CONFIG_OTA_ALLOW_HTTP is not set CONFIG_ESP32S3_DEEP_SLEEP_WAKEUP_DELAY=2000 CONFIG_ESP_SLEEP_DEEP_SLEEP_WAKEUP_DELAY=2000 CONFIG_ESP32S3_RTC_CLK_SRC_INT_RC=y diff --git a/sdkconfig.defaults b/sdkconfig.defaults index de20197..84991c6 100644 --- a/sdkconfig.defaults +++ b/sdkconfig.defaults @@ -1,85 +1,85 @@ -CONFIG_IDF_TARGET="esp32s3" -CONFIG_ESPTOOLPY_FLASHMODE_QIO=y -CONFIG_ESPTOOLPY_FLASHSIZE_4MB=y -CONFIG_PARTITION_TABLE_CUSTOM=y -CONFIG_COMPILER_OPTIMIZATION_PERF=y -CONFIG_SPIRAM=y -CONFIG_SPIRAM_MODE_OCT=y -CONFIG_SPIRAM_FETCH_INSTRUCTIONS=y -CONFIG_SPIRAM_RODATA=y -CONFIG_SPIRAM_SPEED_80M=y -CONFIG_ESP_DEFAULT_CPU_FREQ_MHZ_240=y -CONFIG_ESP32S3_DATA_CACHE_LINE_64B=y -CONFIG_FREERTOS_HZ=1000 -CONFIG_LV_ATTRIBUTE_FAST_MEM_USE_IRAM=y -CONFIG_LV_FONT_MONTSERRAT_12=y -CONFIG_LV_FONT_MONTSERRAT_16=y -CONFIG_LV_FONT_MONTSERRAT_26=y -CONFIG_LV_USE_DEMO_WIDGETS=n -CONFIG_LV_USE_DEMO_BENCHMARK=n -CONFIG_LV_USE_DEMO_STRESS=n -CONFIG_LV_USE_DEMO_MUSIC=n -CONFIG_LV_DEMO_MUSIC_AUTO_PLAY=n - -## LVGL8 ## -CONFIG_LV_MEM_SIZE_KILOBYTES=48 -CONFIG_LV_USE_PERF_MONITOR=y - -## LVGL9 ## -CONFIG_LV_CONF_SKIP=y - -#CLIB default -CONFIG_LV_USE_CLIB_MALLOC=y -CONFIG_LV_USE_CLIB_SPRINTF=y -CONFIG_LV_USE_CLIB_STRING=y - -# Performance monitor -CONFIG_LV_USE_OBSERVER=y -CONFIG_LV_USE_SYSMON=y -CONFIG_LV_USE_PERF_MONITOR=y - -CONFIG_ESP_WIFI_ENABLED=y -CONFIG_ESP_WIFI_STATIC_RX_BUFFER_NUM=10 -CONFIG_ESP_WIFI_DYNAMIC_RX_BUFFER_NUM=32 -# CONFIG_ESP_WIFI_STATIC_TX_BUFFER is not set -CONFIG_ESP_WIFI_DYNAMIC_TX_BUFFER=y -CONFIG_ESP_WIFI_TX_BUFFER_TYPE=1 -CONFIG_ESP_WIFI_DYNAMIC_TX_BUFFER_NUM=32 -CONFIG_ESP_WIFI_STATIC_RX_MGMT_BUFFER=y -# CONFIG_ESP_WIFI_DYNAMIC_RX_MGMT_BUFFER is not set -CONFIG_ESP_WIFI_DYNAMIC_RX_MGMT_BUF=0 -CONFIG_ESP_WIFI_RX_MGMT_BUF_NUM_DEF=5 -# CONFIG_ESP_WIFI_CSI_ENABLED is not set -CONFIG_ESP_WIFI_AMPDU_TX_ENABLED=y -CONFIG_ESP_WIFI_TX_BA_WIN=6 -CONFIG_ESP_WIFI_AMPDU_RX_ENABLED=y -CONFIG_ESP_WIFI_RX_BA_WIN=6 -CONFIG_ESP_WIFI_NVS_ENABLED=y -CONFIG_ESP_WIFI_TASK_PINNED_TO_CORE_0=y -# CONFIG_ESP_WIFI_TASK_PINNED_TO_CORE_1 is not set -CONFIG_ESP_WIFI_SOFTAP_BEACON_MAX_LEN=752 -CONFIG_ESP_WIFI_MGMT_SBUF_NUM=32 -CONFIG_ESP_WIFI_IRAM_OPT=y -# CONFIG_ESP_WIFI_EXTRA_IRAM_OPT is not set -CONFIG_ESP_WIFI_RX_IRAM_OPT=y -CONFIG_ESP_WIFI_ENABLE_WPA3_SAE=y -CONFIG_ESP_WIFI_ENABLE_SAE_PK=y -CONFIG_ESP_WIFI_SOFTAP_SAE_SUPPORT=y -CONFIG_ESP_WIFI_ENABLE_WPA3_OWE_STA=y -# CONFIG_ESP_WIFI_SLP_IRAM_OPT is not set -# CONFIG_ESP_WIFI_FTM_ENABLE is not set -CONFIG_ESP_WIFI_STA_DISCONNECTED_PM_ENABLE=y -# CONFIG_ESP_WIFI_GCMP_SUPPORT is not set -# CONFIG_ESP_WIFI_GMAC_SUPPORT is not set -CONFIG_ESP_WIFI_SOFTAP_SUPPORT=y -# CONFIG_ESP_WIFI_SLP_BEACON_LOST_OPT is not set -CONFIG_ESP_WIFI_ESPNOW_MAX_ENCRYPT_NUM=7 -CONFIG_ESP_WIFI_MBEDTLS_CRYPTO=y -CONFIG_ESP_WIFI_MBEDTLS_TLS_CLIENT=y -# CONFIG_ESP_WIFI_WAPI_PSK is not set -# CONFIG_ESP_WIFI_SUITE_B_192 is not set -# CONFIG_ESP_WIFI_11KV_SUPPORT is not set -# CONFIG_ESP_WIFI_MBO_SUPPORT is not set -# CONFIG_ESP_WIFI_DPP_SUPPORT is not set -# CONFIG_ESP_WIFI_11R_SUPPORT is not set -# CONFIG_ESP_WIFI_WPS_SOFTAP_REGISTRAR is not set +CONFIG_IDF_TARGET="esp32s3" +CONFIG_ESPTOOLPY_FLASHMODE_QIO=y +CONFIG_ESPTOOLPY_FLASHSIZE_4MB=y +CONFIG_PARTITION_TABLE_CUSTOM=y +CONFIG_COMPILER_OPTIMIZATION_PERF=y +CONFIG_SPIRAM=y +CONFIG_SPIRAM_MODE_OCT=y +CONFIG_SPIRAM_FETCH_INSTRUCTIONS=y +CONFIG_SPIRAM_RODATA=y +CONFIG_SPIRAM_SPEED_80M=y +CONFIG_ESP_DEFAULT_CPU_FREQ_MHZ_240=y +CONFIG_ESP32S3_DATA_CACHE_LINE_64B=y +CONFIG_FREERTOS_HZ=1000 +CONFIG_LV_ATTRIBUTE_FAST_MEM_USE_IRAM=y +CONFIG_LV_FONT_MONTSERRAT_12=y +CONFIG_LV_FONT_MONTSERRAT_16=y +CONFIG_LV_FONT_MONTSERRAT_26=y +CONFIG_LV_USE_DEMO_WIDGETS=n +CONFIG_LV_USE_DEMO_BENCHMARK=n +CONFIG_LV_USE_DEMO_STRESS=n +CONFIG_LV_USE_DEMO_MUSIC=n +CONFIG_LV_DEMO_MUSIC_AUTO_PLAY=n + +## LVGL8 ## +CONFIG_LV_MEM_SIZE_KILOBYTES=48 +CONFIG_LV_USE_PERF_MONITOR=y + +## LVGL9 ## +CONFIG_LV_CONF_SKIP=y + +#CLIB default +CONFIG_LV_USE_CLIB_MALLOC=y +CONFIG_LV_USE_CLIB_SPRINTF=y +CONFIG_LV_USE_CLIB_STRING=y + +# Performance monitor +CONFIG_LV_USE_OBSERVER=y +CONFIG_LV_USE_SYSMON=y +CONFIG_LV_USE_PERF_MONITOR=y + +CONFIG_ESP_WIFI_ENABLED=y +CONFIG_ESP_WIFI_STATIC_RX_BUFFER_NUM=10 +CONFIG_ESP_WIFI_DYNAMIC_RX_BUFFER_NUM=32 +# CONFIG_ESP_WIFI_STATIC_TX_BUFFER is not set +CONFIG_ESP_WIFI_DYNAMIC_TX_BUFFER=y +CONFIG_ESP_WIFI_TX_BUFFER_TYPE=1 +CONFIG_ESP_WIFI_DYNAMIC_TX_BUFFER_NUM=32 +CONFIG_ESP_WIFI_STATIC_RX_MGMT_BUFFER=y +# CONFIG_ESP_WIFI_DYNAMIC_RX_MGMT_BUFFER is not set +CONFIG_ESP_WIFI_DYNAMIC_RX_MGMT_BUF=0 +CONFIG_ESP_WIFI_RX_MGMT_BUF_NUM_DEF=5 +# CONFIG_ESP_WIFI_CSI_ENABLED is not set +CONFIG_ESP_WIFI_AMPDU_TX_ENABLED=y +CONFIG_ESP_WIFI_TX_BA_WIN=6 +CONFIG_ESP_WIFI_AMPDU_RX_ENABLED=y +CONFIG_ESP_WIFI_RX_BA_WIN=6 +CONFIG_ESP_WIFI_NVS_ENABLED=y +CONFIG_ESP_WIFI_TASK_PINNED_TO_CORE_0=y +# CONFIG_ESP_WIFI_TASK_PINNED_TO_CORE_1 is not set +CONFIG_ESP_WIFI_SOFTAP_BEACON_MAX_LEN=752 +CONFIG_ESP_WIFI_MGMT_SBUF_NUM=32 +CONFIG_ESP_WIFI_IRAM_OPT=y +# CONFIG_ESP_WIFI_EXTRA_IRAM_OPT is not set +CONFIG_ESP_WIFI_RX_IRAM_OPT=y +CONFIG_ESP_WIFI_ENABLE_WPA3_SAE=y +CONFIG_ESP_WIFI_ENABLE_SAE_PK=y +CONFIG_ESP_WIFI_SOFTAP_SAE_SUPPORT=y +CONFIG_ESP_WIFI_ENABLE_WPA3_OWE_STA=y +# CONFIG_ESP_WIFI_SLP_IRAM_OPT is not set +# CONFIG_ESP_WIFI_FTM_ENABLE is not set +CONFIG_ESP_WIFI_STA_DISCONNECTED_PM_ENABLE=y +# CONFIG_ESP_WIFI_GCMP_SUPPORT is not set +# CONFIG_ESP_WIFI_GMAC_SUPPORT is not set +CONFIG_ESP_WIFI_SOFTAP_SUPPORT=y +# CONFIG_ESP_WIFI_SLP_BEACON_LOST_OPT is not set +CONFIG_ESP_WIFI_ESPNOW_MAX_ENCRYPT_NUM=7 +CONFIG_ESP_WIFI_MBEDTLS_CRYPTO=y +CONFIG_ESP_WIFI_MBEDTLS_TLS_CLIENT=y +# CONFIG_ESP_WIFI_WAPI_PSK is not set +# CONFIG_ESP_WIFI_SUITE_B_192 is not set +# CONFIG_ESP_WIFI_11KV_SUPPORT is not set +# CONFIG_ESP_WIFI_MBO_SUPPORT is not set +# CONFIG_ESP_WIFI_DPP_SUPPORT is not set +# CONFIG_ESP_WIFI_11R_SUPPORT is not set +# CONFIG_ESP_WIFI_WPS_SOFTAP_REGISTRAR is not set diff --git a/sdkconfig.old b/sdkconfig.old index 1b23dc2..cebf5df 100644 --- a/sdkconfig.old +++ b/sdkconfig.old @@ -548,6 +548,49 @@ CONFIG_ESP_WIFI_AUTH_WPA2_PSK=y # CONFIG_ESP_WIFI_AUTH_WAPI_PSK is not set # end of Example Configuration +# +# Example Connection Configuration +# +CONFIG_ENV_GPIO_RANGE_MIN=0 +CONFIG_ENV_GPIO_RANGE_MAX=48 +CONFIG_ENV_GPIO_IN_RANGE_MAX=48 +CONFIG_ENV_GPIO_OUT_RANGE_MAX=48 +CONFIG_EXAMPLE_CONNECT_WIFI=y +# CONFIG_EXAMPLE_WIFI_SSID_PWD_FROM_STDIN is not set +CONFIG_EXAMPLE_PROVIDE_WIFI_CONSOLE_CMD=y +CONFIG_EXAMPLE_WIFI_SSID="myssid" +CONFIG_EXAMPLE_WIFI_PASSWORD="mypassword" +CONFIG_EXAMPLE_WIFI_CONN_MAX_RETRY=6 +# CONFIG_EXAMPLE_WIFI_SCAN_METHOD_FAST is not set +CONFIG_EXAMPLE_WIFI_SCAN_METHOD_ALL_CHANNEL=y + +# +# WiFi Scan threshold +# +CONFIG_EXAMPLE_WIFI_SCAN_RSSI_THRESHOLD=-127 +CONFIG_EXAMPLE_WIFI_AUTH_OPEN=y +# CONFIG_EXAMPLE_WIFI_AUTH_WEP is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA2_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA_WPA2_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA2_ENTERPRISE is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA3_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WPA2_WPA3_PSK is not set +# CONFIG_EXAMPLE_WIFI_AUTH_WAPI_PSK is not set +# end of WiFi Scan threshold + +CONFIG_EXAMPLE_WIFI_CONNECT_AP_BY_SIGNAL=y +# CONFIG_EXAMPLE_WIFI_CONNECT_AP_BY_SECURITY is not set +# CONFIG_EXAMPLE_CONNECT_ETHERNET is not set +# CONFIG_EXAMPLE_CONNECT_PPP is not set +CONFIG_EXAMPLE_CONNECT_IPV4=y +CONFIG_EXAMPLE_CONNECT_IPV6=y +CONFIG_EXAMPLE_CONNECT_IPV6_PREF_LOCAL_LINK=y +# CONFIG_EXAMPLE_CONNECT_IPV6_PREF_GLOBAL is not set +# CONFIG_EXAMPLE_CONNECT_IPV6_PREF_SITE_LOCAL is not set +# CONFIG_EXAMPLE_CONNECT_IPV6_PREF_UNIQUE_LOCAL is not set +# end of Example Connection Configuration + # # Compiler options # @@ -582,6 +625,12 @@ CONFIG_COMPILER_ORPHAN_SECTIONS_PLACE=y # Component config # +# +# Console Library +# +# CONFIG_CONSOLE_SORTED_HELP is not set +# end of Console Library + # # Driver Configurations # @@ -680,6 +729,7 @@ CONFIG_ESP_COEX_ENABLED=y # Common ESP-related # CONFIG_ESP_ERR_TO_NAME_LOOKUP=y +CONFIG_ESP_ALLOW_BSS_SEG_EXTERNAL_MEMORY=y # end of Common ESP-related # @@ -775,6 +825,18 @@ CONFIG_SPI_SLAVE_ISR_IN_IRAM=y CONFIG_USJ_ENABLE_USB_SERIAL_JTAG=y # end of ESP-Driver:USB Serial/JTAG Configuration +# +# Ethernet +# +CONFIG_ETH_ENABLED=y +CONFIG_ETH_USE_SPI_ETHERNET=y +# CONFIG_ETH_SPI_ETHERNET_DM9051 is not set +# CONFIG_ETH_SPI_ETHERNET_W5500 is not set +# CONFIG_ETH_SPI_ETHERNET_KSZ8851SNL is not set +# CONFIG_ETH_USE_OPENETH is not set +# CONFIG_ETH_TRANSMIT_MUTEX is not set +# end of Ethernet + # # Event Loop Library # @@ -786,12 +848,19 @@ CONFIG_ESP_EVENT_POST_FROM_IRAM_ISR=y # # ESP HTTP client # -# CONFIG_ESP_HTTP_CLIENT_ENABLE_HTTPS is not set +CONFIG_ESP_HTTP_CLIENT_ENABLE_HTTPS=y # CONFIG_ESP_HTTP_CLIENT_ENABLE_BASIC_AUTH is not set # CONFIG_ESP_HTTP_CLIENT_ENABLE_DIGEST_AUTH is not set # CONFIG_ESP_HTTP_CLIENT_ENABLE_CUSTOM_TRANSPORT is not set # end of ESP HTTP client +# +# ESP HTTPS OTA +# +# CONFIG_ESP_HTTPS_OTA_DECRYPT_CB is not set +# CONFIG_ESP_HTTPS_OTA_ALLOW_HTTP is not set +# end of ESP HTTPS OTA + # # Hardware Settings # @@ -952,14 +1021,13 @@ CONFIG_SPIRAM_ALLOW_STACK_EXTERNAL_MEMORY=y CONFIG_SPIRAM_CLK_IO=30 CONFIG_SPIRAM_CS_IO=26 # CONFIG_SPIRAM_XIP_FROM_PSRAM is not set -CONFIG_SPIRAM_FETCH_INSTRUCTIONS=y -CONFIG_SPIRAM_RODATA=y +# CONFIG_SPIRAM_FETCH_INSTRUCTIONS is not set +# CONFIG_SPIRAM_RODATA is not set CONFIG_SPIRAM_SPEED_80M=y # CONFIG_SPIRAM_SPEED_40M is not set CONFIG_SPIRAM_SPEED=80 # CONFIG_SPIRAM_ECC_ENABLE is not set CONFIG_SPIRAM_BOOT_INIT=y -# CONFIG_SPIRAM_IGNORE_NOTFOUND is not set # CONFIG_SPIRAM_USE_MEMMAP is not set # CONFIG_SPIRAM_USE_CAPS_ALLOC is not set CONFIG_SPIRAM_USE_MALLOC=y @@ -967,7 +1035,7 @@ CONFIG_SPIRAM_MEMTEST=y CONFIG_SPIRAM_MALLOC_ALWAYSINTERNAL=16384 # CONFIG_SPIRAM_TRY_ALLOCATE_WIFI_LWIP is not set CONFIG_SPIRAM_MALLOC_RESERVE_INTERNAL=32768 -# CONFIG_SPIRAM_ALLOW_BSS_SEG_EXTERNAL_MEMORY is not set +CONFIG_SPIRAM_ALLOW_BSS_SEG_EXTERNAL_MEMORY=y # end of SPI RAM config # end of ESP PSRAM @@ -1040,7 +1108,7 @@ CONFIG_ESP_SYSTEM_MEMPROT_FEATURE_LOCK=y CONFIG_ESP_SYSTEM_EVENT_QUEUE_SIZE=32 CONFIG_ESP_SYSTEM_EVENT_TASK_STACK_SIZE=4608 -CONFIG_ESP_MAIN_TASK_STACK_SIZE=40000 +CONFIG_ESP_MAIN_TASK_STACK_SIZE=30000 CONFIG_ESP_MAIN_TASK_AFFINITY_CPU0=y # CONFIG_ESP_MAIN_TASK_AFFINITY_CPU1 is not set # CONFIG_ESP_MAIN_TASK_AFFINITY_NO_AFFINITY is not set @@ -1139,9 +1207,9 @@ CONFIG_ESP_WIFI_TASK_PINNED_TO_CORE_0=y # CONFIG_ESP_WIFI_TASK_PINNED_TO_CORE_1 is not set CONFIG_ESP_WIFI_SOFTAP_BEACON_MAX_LEN=752 CONFIG_ESP_WIFI_MGMT_SBUF_NUM=32 -CONFIG_ESP_WIFI_IRAM_OPT=y +# CONFIG_ESP_WIFI_IRAM_OPT is not set # CONFIG_ESP_WIFI_EXTRA_IRAM_OPT is not set -CONFIG_ESP_WIFI_RX_IRAM_OPT=y +# CONFIG_ESP_WIFI_RX_IRAM_OPT is not set CONFIG_ESP_WIFI_ENABLE_WPA3_SAE=y CONFIG_ESP_WIFI_ENABLE_SAE_PK=y CONFIG_ESP_WIFI_SOFTAP_SAE_SUPPORT=y @@ -1305,11 +1373,9 @@ CONFIG_HAL_SPI_SLAVE_FUNC_IN_IRAM=y CONFIG_HEAP_POISONING_DISABLED=y # CONFIG_HEAP_POISONING_LIGHT is not set # CONFIG_HEAP_POISONING_COMPREHENSIVE is not set -# CONFIG_HEAP_TRACING_OFF is not set +CONFIG_HEAP_TRACING_OFF=y # CONFIG_HEAP_TRACING_STANDALONE is not set -CONFIG_HEAP_TRACING_TOHOST=y -CONFIG_HEAP_TRACING=y -CONFIG_HEAP_TRACING_STACK_DEPTH=2 +# CONFIG_HEAP_TRACING_TOHOST is not set # CONFIG_HEAP_USE_HOOKS is not set # CONFIG_HEAP_TASK_TRACKING is not set # CONFIG_HEAP_ABORT_WHEN_ALLOCATION_FAILS is not set @@ -1326,10 +1392,10 @@ CONFIG_LOG_DEFAULT_LEVEL_INFO=y # CONFIG_LOG_DEFAULT_LEVEL_DEBUG is not set # CONFIG_LOG_DEFAULT_LEVEL_VERBOSE is not set CONFIG_LOG_DEFAULT_LEVEL=3 -CONFIG_LOG_MAXIMUM_EQUALS_DEFAULT=y -# CONFIG_LOG_MAXIMUM_LEVEL_DEBUG is not set +# CONFIG_LOG_MAXIMUM_EQUALS_DEFAULT is not set +CONFIG_LOG_MAXIMUM_LEVEL_DEBUG=y # CONFIG_LOG_MAXIMUM_LEVEL_VERBOSE is not set -CONFIG_LOG_MAXIMUM_LEVEL=3 +CONFIG_LOG_MAXIMUM_LEVEL=4 # CONFIG_LOG_MASTER_LEVEL is not set CONFIG_LOG_COLORS=y CONFIG_LOG_TIMESTAMP_SOURCE_RTOS=y @@ -1648,25 +1714,21 @@ CONFIG_MBEDTLS_ERROR_STRINGS=y # CONFIG_MQTT_PROTOCOL_311=y # CONFIG_MQTT_PROTOCOL_5 is not set -CONFIG_MQTT_TRANSPORT_SSL=y -CONFIG_MQTT_TRANSPORT_WEBSOCKET=y -CONFIG_MQTT_TRANSPORT_WEBSOCKET_SECURE=y +# CONFIG_MQTT_TRANSPORT_SSL is not set +# CONFIG_MQTT_TRANSPORT_WEBSOCKET is not set # CONFIG_MQTT_MSG_ID_INCREMENTAL is not set # CONFIG_MQTT_SKIP_PUBLISH_IF_DISCONNECTED is not set # CONFIG_MQTT_REPORT_DELETED_MESSAGES is not set CONFIG_MQTT_USE_CUSTOM_CONFIG=y CONFIG_MQTT_TCP_DEFAULT_PORT=1883 -CONFIG_MQTT_SSL_DEFAULT_PORT=8883 -CONFIG_MQTT_WS_DEFAULT_PORT=80 -CONFIG_MQTT_WSS_DEFAULT_PORT=443 -CONFIG_MQTT_BUFFER_SIZE=1024 -CONFIG_MQTT_TASK_STACK_SIZE=6144 +CONFIG_MQTT_BUFFER_SIZE=100 +CONFIG_MQTT_TASK_STACK_SIZE=4096 # CONFIG_MQTT_DISABLE_API_LOCKS is not set CONFIG_MQTT_TASK_PRIORITY=5 CONFIG_MQTT_POLL_READ_TIMEOUT_MS=10000 CONFIG_MQTT_EVENT_QUEUE_SIZE=1 # CONFIG_MQTT_TASK_CORE_SELECTION_ENABLED is not set -# CONFIG_MQTT_OUTBOX_DATA_ON_EXTERNAL_MEMORY is not set +CONFIG_MQTT_OUTBOX_DATA_ON_EXTERNAL_MEMORY=y # CONFIG_MQTT_CUSTOM_OUTBOX is not set CONFIG_MQTT_OUTBOX_EXPIRED_TIMEOUT_MS=30000 # end of ESP-MQTT Configurations @@ -1828,6 +1890,19 @@ CONFIG_WL_SECTOR_SIZE_4096=y CONFIG_WL_SECTOR_SIZE=4096 # end of Wear Levelling +# +# WiFi Logger configuration +# +# CONFIG_TRANSPORT_PROTOCOL_UDP is not set +CONFIG_TRANSPORT_PROTOCOL_TCP=y +# CONFIG_TRANSPORT_PROTOCOL_WEBSOCKET is not set +CONFIG_ROUTE_ESP_IDF_API_LOGS_TO_WIFI=y +CONFIG_SERVER_IP_ADDRESS="192.168.0.28" +CONFIG_SERVER_PORT=9999 +CONFIG_MESSAGE_QUEUE_SIZE=1000 +CONFIG_BUFFER_SIZE=512 +# end of WiFi Logger configuration + # # ESP LCD TOUCH # @@ -1835,6 +1910,39 @@ CONFIG_ESP_LCD_TOUCH_MAX_POINTS=1 CONFIG_ESP_LCD_TOUCH_MAX_BUTTONS=1 # end of ESP LCD TOUCH +# +# ESP WebSocket client +# +# CONFIG_ESP_WS_CLIENT_ENABLE_DYNAMIC_BUFFER is not set +# end of ESP WebSocket client + +# +# LittleFS +# +# CONFIG_LITTLEFS_SDMMC_SUPPORT is not set +CONFIG_LITTLEFS_MAX_PARTITIONS=3 +CONFIG_LITTLEFS_PAGE_SIZE=256 +CONFIG_LITTLEFS_OBJ_NAME_LEN=64 +CONFIG_LITTLEFS_READ_SIZE=128 +CONFIG_LITTLEFS_WRITE_SIZE=128 +CONFIG_LITTLEFS_LOOKAHEAD_SIZE=128 +CONFIG_LITTLEFS_CACHE_SIZE=512 +CONFIG_LITTLEFS_BLOCK_CYCLES=512 +CONFIG_LITTLEFS_USE_MTIME=y +# CONFIG_LITTLEFS_USE_ONLY_HASH is not set +# CONFIG_LITTLEFS_HUMAN_READABLE is not set +CONFIG_LITTLEFS_MTIME_USE_SECONDS=y +# CONFIG_LITTLEFS_MTIME_USE_NONCE is not set +# CONFIG_LITTLEFS_SPIFFS_COMPAT is not set +# CONFIG_LITTLEFS_FLUSH_FILE_EVERY_WRITE is not set +# CONFIG_LITTLEFS_FCNTL_GET_PATH is not set +# CONFIG_LITTLEFS_MULTIVERSION is not set +# CONFIG_LITTLEFS_MALLOC_STRATEGY_DISABLE is not set +CONFIG_LITTLEFS_MALLOC_STRATEGY_DEFAULT=y +# CONFIG_LITTLEFS_MALLOC_STRATEGY_INTERNAL is not set +CONFIG_LITTLEFS_ASSERTS=y +# end of LittleFS + # # LVGL configuration # @@ -1855,8 +1963,8 @@ CONFIG_LV_COLOR_DEPTH=16 # # Memory Settings # -CONFIG_LV_USE_BUILTIN_MALLOC=y -# CONFIG_LV_USE_CLIB_MALLOC is not set +# CONFIG_LV_USE_BUILTIN_MALLOC is not set +CONFIG_LV_USE_CLIB_MALLOC=y # CONFIG_LV_USE_MICROPYTHON_MALLOC is not set # CONFIG_LV_USE_RTTHREAD_MALLOC is not set # CONFIG_LV_USE_CUSTOM_MALLOC is not set @@ -1866,9 +1974,6 @@ CONFIG_LV_USE_BUILTIN_STRING=y # CONFIG_LV_USE_BUILTIN_SPRINTF is not set CONFIG_LV_USE_CLIB_SPRINTF=y # CONFIG_LV_USE_CUSTOM_SPRINTF is not set -CONFIG_LV_MEM_SIZE_KILOBYTES=64 -CONFIG_LV_MEM_POOL_EXPAND_SIZE_KILOBYTES=0 -CONFIG_LV_MEM_ADR=0x0 # end of Memory Settings # @@ -2272,6 +2377,7 @@ CONFIG_STACK_CHECK_NONE=y # CONFIG_EVENT_LOOP_PROFILING is not set CONFIG_POST_EVENTS_FROM_ISR=y CONFIG_POST_EVENTS_FROM_IRAM_ISR=y +# CONFIG_OTA_ALLOW_HTTP is not set CONFIG_ESP32S3_DEEP_SLEEP_WAKEUP_DELAY=2000 CONFIG_ESP_SLEEP_DEEP_SLEEP_WAKEUP_DELAY=2000 CONFIG_ESP32S3_RTC_CLK_SRC_INT_RC=y @@ -2296,7 +2402,7 @@ CONFIG_ESP32S3_DEFAULT_CPU_FREQ_240=y CONFIG_ESP32S3_DEFAULT_CPU_FREQ_MHZ=240 CONFIG_SYSTEM_EVENT_QUEUE_SIZE=32 CONFIG_SYSTEM_EVENT_TASK_STACK_SIZE=4608 -CONFIG_MAIN_TASK_STACK_SIZE=40000 +CONFIG_MAIN_TASK_STACK_SIZE=30000 CONFIG_CONSOLE_UART_DEFAULT=y # CONFIG_CONSOLE_UART_CUSTOM is not set # CONFIG_CONSOLE_UART_NONE is not set @@ -2356,8 +2462,8 @@ CONFIG_ESP32_WIFI_TASK_PINNED_TO_CORE_0=y # CONFIG_ESP32_WIFI_TASK_PINNED_TO_CORE_1 is not set CONFIG_ESP32_WIFI_SOFTAP_BEACON_MAX_LEN=752 CONFIG_ESP32_WIFI_MGMT_SBUF_NUM=32 -CONFIG_ESP32_WIFI_IRAM_OPT=y -CONFIG_ESP32_WIFI_RX_IRAM_OPT=y +# CONFIG_ESP32_WIFI_IRAM_OPT is not set +# CONFIG_ESP32_WIFI_RX_IRAM_OPT is not set CONFIG_ESP32_WIFI_ENABLE_WPA3_SAE=y CONFIG_ESP32_WIFI_ENABLE_WPA3_OWE_STA=y CONFIG_WPA_MBEDTLS_CRYPTO=y