MicroPython examples for V7?

Hi Amir,
As promised, I tried to combine both demo_printer versions into one. It was quite a bit of work, because I had to re-calculate all the widget sizes and their positions but it was not particularly difficult. In the original C program they are defined as absolute values and I now had to calculate them depending on the horizontal and vertical resolution.
The new demo_printer version uses argb8888 images for the 800x480 resolution and png images for the 320x240 resolution.
I could not read the parrot png image in its full size even though there was enough free memory on the heap.
Then there is still the problem that absolute file addresses given to fs_driver end up without the initial “/” in the open callback for which I only implemented a dirty work-around.
To try out, just check the last 2 lines of demo_printer.py where the resolution is set.

Nice work!! :clap:

I just tried it out:
The unix port “just works”, on both high and low resolutions! Very nice!

The ESP32 version works as well.
I needed to add a few lines to register the display and touch driver with the specific parameters for my board.

I noticed, however, that it’s extremely slow.
It takes more than 20 seconds just to load and display the first screen. From that point it works, but slowly.
My guess is that this is a result of the many images and fonts. They are all stored on SPI-RAM which is a slow memory. The ESP32 caches it but when when a lot of images are used, caching does not help much.
I’m not sure if there is anything we can do to improve that assuming we must use the SPI-RAM for storing all the images and fonts. (We can change SPI-RAM to 80mhz QIO, which would boost it a bit but might not work for all boards. The safe default it 40Mhz DIO).

Did you experience the same when trying to run this on ESP32?

By the way, you can remove fs_driver.py and imagetools.py from the example, they are now frozen modules so always available when using latest lv_micropython.

Anyway - great work!!
An excellent contribution to the LVGL community!

Thanks for the applause.
I will take away imagetools.py but I still have problems with fs_driver.py. When using absolute filenames the preceding “/” gets lost in the open callback. Can you check?
Concerning the ESP32 slowness, there are several tricks we can try to play:

  • Use argb files instead of png (no decoding)
  • Use rgb files for those images that do not need opacity (reduces size by 25%)
  • Pre-compile the code and use mpy files
  • Check if the font is already enabled in lv_conf.h and dynamically load fonts only if necessary. For speed reasons we should enable the fonts in the ESP32 version.
  • Write another image converter converting the images into Python source code (as is done in C) and store as many of the images as possible in flash.
    Let me try. I will come back to you as soon as I see any results.

I just tried the new lv_micropython version with imagetools.py frozen into the unix binary. I see that the images are read from their png files but the don’t appear on the screen. When I put back imagetools.py into the demo_printer directory everything works fine.

@amirgon @uraich This might be a bad question (not an ESP32 user) but is using the internal flash as a filesystem supported? If so, couldn’t you store the standard LVGL .bin image files there and then use some mmap-like equivalent to read them straight from flash without needing to store them in RAM? That would save you needing to write any additional converter logic.

LVGL removes leading / in lv_fs_get_real_path:

I’m not sure why it was designed to remove all leading /.
Perhaps @kisvegabor or @embeddedt would know.

Strange, it worked for me with the frozen imagetools.py.
Are you using the latest lv_micropython? Did you try to clean and rebuild it?

Yes, of course.

The filesystem does not allow something like mmap, as far as I know.
You can, however, store data on flash (not on the filesystem partition) and access it as memory (the flash is mapped into the address space). This is how constant globals are accessed when they are initialized on the “data” linker section.
This is what happens when images/fonts are compiled as C files.

We can use binary images directly, but PNG are compressed, more portable and easier to use. Also, we already have automatic conversion from PNG to several color modes so the same PNG file works seamlessly on both linux and ESP32, while we would need different binary files for the same image on linux and ESP32 because they use different color modes.

When using a single script that “just works” everywhere (on different platforms) I think that it’s easier to use PNG files, although it’s probably possible to use the 32bit binary image format and use the conversion functions to convert it to different platforms.

See lv_fs_open forces all file paths to be relative · Issue #2007 · lvgl/lvgl · GitHub.

I see.
It can certainly confuse the users.
I would vote for fixing it in the next release.
I agree there should be a consistent behavior, but preferably one that is intuitive for most users.

I have added the remaining examples. The majority appear to be working without any issues!

I noticed that the imgbtn one is having problems as the current open() implementation seems to need an https:// prefix. I tried adding the GitHub URL to sys.path but that didn’t seem to help, probably because open doesn’t use sys.path for finding files.

The patched version can be found here, and the broken version is in the docs.

Great! Thank you for this effort @embeddedt!

In addition to lv_imgbtn, I’ve also noticed some problems with lv_cont, modal lv_msgbox, lv_line, lv_img, lv_canvas, lv_gauge and lv_objmask.

Yesterday I downloaded the latest lv_micropython and built it. The problem with the frozen imagetool.py remains (the png files are loaded but I don’t see the images). I also had to keep my fs_driver version in which I add the missing initial ‘/’ if the path does not start with ‘./’
Concerning speed on the esp32 I can try to avoid dynamic font loading if the font is defined in lv_conf.h and I can try to avoid image loading if the image dscs are available as Python source files. The image converter is already working and I can easily convert argb8888 files into Python source code. I can also try to compile into byte code to improve startup speed.

I wasn’t able to reproduce, I’ll try again later when I have more time.

We might want to consider making this change to the frozen fs_driver, if this can be done in a way that is backward compatible because I wouldn’t want to break code that already relies on the current behavior.

As long as the demo can “just run” (although slower) without the need to rebuild the firmware that’s fine. So it make it run faster, the user would need to rebuild the firmware, but it would still work if he does not.

I’m not sure I understand. I can see how images can be loaded more efficiently when they are built as C files. But how do you plan to do the same thing with Python files?

Hi Amir,
I tried plenty of different things to speed up the demo_printer on the esp32.
Removing logging: very little effect
Replacing png by: argb565: Very little effect. argb565 file don’t need decompression but are bigger and take longer to read.
This however worked: cross-compile demo_printer.py and theme.py into byte-code and upload this instead of the source code: It improved the time to the first screen by 1/2.
Concerning fs_driver.py, I think the only good solution would be to change in lvgl. The problem is that I cannot distinguish between absolute and relative paths and the root directory changes in the unix port if you run the script from a different directory. My hack to add the ‘/’ if the path does not start with ‘./’ works if you give an absolute path name but not if the path is relative.
To give you an idea of what I meant when I said that I could try to include the images as Python source source I added imgTestPyInclude.py to the demo_printer folder. It should “just run” under the SDL driver.
I think it is more important now to make lv_micropython work under the new lvgl-v8 and to switch to the new cmake based build system. Is there anything where I can help?

I fixed the / trimming issue in v8. See https://github.com/lvgl/lvgl/issues/2007#issuecomment-801375134

Actually I’m using mostly compiled .mpy for my projects.
The improved load time also depends on this PR which was not accepted in upstream yet, but I’ve integrated it into lv_micropython.

I can’t find it there. Did you push it to GitHub?

We have discussions over Micropython for v8 on:

There are still a few questions open, but I think we are ready to start trying the bindings on v8.
I’m planning to start working on that soon.

Regarding CMake (only relevant to ESP32) I actually started working on that.
It requires rewriting the makefile rules in CMake language. I’m planning to have a CMakeLists.txt on lv_micropython_bindings root which will take care of running the bindings script etc. which is nicer than what we have today where Micropython’s makefile contains LVGL bindings rules.
However we will not get rid of Makefiles yet because the other ports (unix, stm32) are still relying on Makefiles.

Actually I’m giving it a higher priority because I need esp-idf 4.2 working with lv_micropython so I’m working on that first and then plan to move on to v8.

We would definitely be glad to get you help there! Thanks!
There is a lot of work to do. I will let you know when I start working on that.

Oups, sorry! Something went wrong when pushing. imgTestPyInclude.py is up there now.
In fact I am very interested in your CMake files. The current Micropython CMakelists do not allow to integrate user_modules in C easily, as was the case with the Makefiles.
In any case I intend to go through the Micropython lv_examples and make sure they also work in V8.

How loading a python file (even in bytecode format) more efficient than loading a binary file from the file system?
I can see the benefit only if the python file is frozen.

I’m setting EXTRA_COMPONENT_DIRS with two new components: LVGL and the bindings.

That would be great! :+1:

Bonjour ,
some news about this locking point ?
“The current Micropython CMakelists do not allow to integrate user_modules in C easily, as was the case with the Makefiles.”
Thanks

The Micropython bindings do not rely on user_modules support.

I’m currently working on integrating lv_micropython with newer version of Micropython with cmake build system for ESP32.

OK
ESP32 in t-watch use st7789 C speed driver as user_module
And with lv_micropython it 's better

Who do I speak to ?

Hi @uraich

I just pushed a dev-8.0 branch to lv_micropython.
This branch integrates latest LVGL v8.0-dev and latest Micropython v1.15, including the new CMake build system for ESP32 (so you can use recent ESP-IDF versions).

I’ve migrated advanced_demo.py to LVGL v8 and tested it on both the unix and ESP32 ports. It works well, although there are still number of open issues we are discussing on #1763. I’ve also started using there some new features such as the flex styles.

Would you like to have a look?

There is plenty of work still left to do testing v8 features on Micropython and migrating the examples to v8, we could really use your help, if you are available for this.