rm-hull / luma.lcd

Python module to drive PCD8544, HT1621, ST7735, ST7567 and UC1701X-based LCDs
https://luma-lcd.readthedocs.io
MIT License
156 stars 56 forks source link

ili9341 and PWM support? #131

Closed mattblovell closed 3 years ago

mattblovell commented 3 years ago

As seems to be a habit of mine, this isn't actually a problem with luma.lcd, it's another question...

Per Version 1.11 of the ILI9341 datasheet attached below, that controller appears to have its own LEDPWM output pin. Of the several Backlight Control Registers, Backlight Control 7 provides the PWM_DIV[7:0] value to use. Further details appear in Section 8.3.14 (pdf page 176)

At present I have no way of knowing whether the display module I have makes use of that LEDPWM output or is driving the backlight LEDs via some other mechanism. If the controller itself provides appropriate drivers, though, it seems like that might be a less-expensive implementation than other approaches.

Does luma.lcd initialization of ILI9341 controllers touch the Backlight Control registers at all? It might be interesting to try, then "redirect" the existing PWM method calls to alter Backlight Control 7 programming. I can investigate further as I have the time.

My whole reason for bringing the topic up is that RPi.GPIO's current implementation (for both the native RPi version and in the Odroid-specific fork) uses a pthreads-based approach for PWM. When I've tried it, the resulting brightness flicker is more distracting than just having a too-bright display.

ILI9341_v1.11.pdf

mattblovell commented 3 years ago

I can investigate further as I have the time.

From what I can tell, the particular display module I have is not using the ILI9341's backlight control in any fashion. About the only command I could issue that had any noticeable effect was:

device.command(0x21)  # Display Inversion

and that wasn't of much particular use! :)

Seems somewhat of a shame, since the ILI9341 appears to offer adjustable brightness settings, as well as controlled transitions whenever brightness changes occur. I guess I'll have to be more selective the next time I'm shopping for displays (as opposed to just crossing fingers and hoping some random display will at least work).

I'll let this issue remain open a few days in case @rm-hull wants to comment at all.


BTW, on a slightly different topic, poking around within the Linux kernel's drivers/gpu/drm/tiny directory (well, the copy of it that exists on github):

https://github.com/torvalds/linux/tree/master/drivers/gpu/drm/tiny

I noticed that luma.lcd's initialization code appears to match that in the ili9341.c driver. The mi0283qt.c driver is also intended for ILI9341 controllers (I'm using it in my dtoverlay / framebuffer experiments), and it uses slightly different gamma correction values than ili9341.c. It could just be confirmation bias, but I think the color accuracy is a bit better with the values from mi0283qt.c.

I'm using those values in my script just by issuing commands at startup:

    if CHANGE_GAMMA:
        # Use the gamma settings from Linux's mi0283qt.c driver
        device.command(0xe0,                                # Set Gamma (+ polarity)
            0x1f, 0x1a, 0x18, 0x0a, 0x0f, 0x06, 0x45, 0x87,
            0x32, 0x0a, 0x07, 0x02, 0x07, 0x05, 0x00)
        device.command(0xe1,                                # Set Gamma (- polarity)
            0x00, 0x25, 0x27, 0x05, 0x10, 0x09, 0x3a, 0x78,
            0x4d, 0x05, 0x18, 0x0d, 0x38, 0x3a, 0x1f)