diff --git a/src/drivers/St7789.cpp b/src/drivers/St7789.cpp index cdfa6a34..0df19b45 100644 --- a/src/drivers/St7789.cpp +++ b/src/drivers/St7789.cpp @@ -25,6 +25,9 @@ void St7789::Init() { #ifndef DRIVER_DISPLAY_MIRROR DisplayInversionOn(); #endif + PorchSet(); + FrameRateNormalSet(); + IdleFrameRateOff(); NormalModeOn(); SetVdv(); PowerControl(); @@ -149,27 +152,44 @@ void St7789::IdleModeOff() { WriteCommand(static_cast(Commands::IdleModeOff)); } -void St7789::FrameRateLow() { - WriteCommand(static_cast(Commands::FrameRate)); - // Enable frame rate control for partial/idle mode, 8x frame divider +void St7789::PorchSet() { + WriteCommand(static_cast(Commands::Porch)); + constexpr uint8_t args[] = { + 0x02, // Normal mode front porch + 0x03, // Normal mode back porch + 0x01, // Porch control enable + 0xed, // Idle mode front:back porch + 0xed, // Partial mode front:back porch (partial mode unused but set anyway) + }; + WriteData(args, sizeof(args)); +} + +void St7789::FrameRateNormalSet() { + WriteCommand(static_cast(Commands::FrameRateNormal)); + // Note that the datasheet table is imprecise - see formula below table + WriteData(0x0a); +} + +void St7789::IdleFrameRateOn() { + WriteCommand(static_cast(Commands::FrameRateIdle)); // According to the datasheet, these controls should apply only to partial/idle mode // However they appear to apply to normal mode, so we have to enable/disable // every time we enter/exit always on // In testing this divider appears to actually be 16x? constexpr uint8_t args[] = { 0x13, // Enable frame rate control for partial/idle mode, 8x frame divider - 0x1f, // Idle mode frame rate (lowest possible) - 0x1f, // Partial mode frame rate (lowest possible, unused) + 0x1e, // Idle mode frame rate + 0x1e, // Partial mode frame rate (unused) }; WriteData(args, sizeof(args)); } -void St7789::FrameRateNormal() { - WriteCommand(static_cast(Commands::FrameRate)); +void St7789::IdleFrameRateOff() { + WriteCommand(static_cast(Commands::FrameRateIdle)); constexpr uint8_t args[] = { 0x00, // Disable frame rate control and divider - 0x0f, // Idle mode frame rate (normal) - 0x0f, // Partial mode frame rate (normal, unused) + 0x0a, // Idle mode frame rate (normal) + 0x0a, // Partial mode frame rate (normal, unused) }; WriteData(args, sizeof(args)); } @@ -266,13 +286,13 @@ void St7789::HardwareReset() { void St7789::LowPowerOn() { IdleModeOn(); - FrameRateLow(); + IdleFrameRateOn(); NRF_LOG_INFO("[LCD] Low power mode"); } void St7789::LowPowerOff() { IdleModeOff(); - FrameRateNormal(); + IdleFrameRateOff(); NRF_LOG_INFO("[LCD] Normal power mode"); } diff --git a/src/drivers/St7789.h b/src/drivers/St7789.h index 96d16b93..9c778905 100644 --- a/src/drivers/St7789.h +++ b/src/drivers/St7789.h @@ -50,12 +50,14 @@ namespace Pinetime { void WriteToRam(const uint8_t* data, size_t size); void IdleModeOn(); void IdleModeOff(); - void FrameRateNormal(); - void FrameRateLow(); + void FrameRateNormalSet(); + void IdleFrameRateOff(); + void IdleFrameRateOn(); void DisplayOn(); void DisplayOff(); void PowerControl(); void GateControl(); + void PorchSet(); void SetAddrWindow(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t y1); void SetVdv(); @@ -80,12 +82,14 @@ namespace Pinetime { IdleModeOff = 0x38, IdleModeOn = 0x39, PixelFormat = 0x3a, - FrameRate = 0xb3, + FrameRateIdle = 0xb3, + FrameRateNormal = 0xc6, VdvSet = 0xc4, Command2Enable = 0xdf, PowerControl1 = 0xd0, PowerControl2 = 0xe8, GateControl = 0xb7, + Porch = 0xb2, }; void WriteData(uint8_t data); void WriteData(const uint8_t* data, size_t size);