Skip to content

Commit

Permalink
Fix screen animation errors (testing with actual ST7789)
Browse files Browse the repository at this point in the history
Removed the notification to protect the data/cmd lcd pin, instead stuffed that logic inside the mutex of the Spi driver... This probably isn't the BEST way to do it, but it's working great for now.
  • Loading branch information
Quantum-cross committed Oct 14, 2021
1 parent ce63f51 commit ce23767
Show file tree
Hide file tree
Showing 11 changed files with 58 additions and 52 deletions.
2 changes: 1 addition & 1 deletion src/components/gfx/Gfx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -184,7 +184,7 @@ void Gfx::NotifyEndOfTransfer(TaskHandle_t task) {
}

void Gfx::WaitTransferFinished() const {
ulTaskNotifyTake(pdTRUE, 500);
// ulTaskNotifyTake(pdTRUE, 500);
}

void Gfx::SetScrollArea(uint16_t topFixedLines, uint16_t scrollLines, uint16_t bottomFixedLines) {
Expand Down
2 changes: 1 addition & 1 deletion src/displayapp/DisplayApp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,7 @@ void DisplayApp::Process(void* instance) {
app->InitHw();

// Send a dummy notification to unlock the lvgl display driver for the first iteration
xTaskNotifyGive(xTaskGetCurrentTaskHandle());
// xTaskNotifyGive(xTaskGetCurrentTaskHandle());

while (true) {
app->Refresh();
Expand Down
6 changes: 3 additions & 3 deletions src/displayapp/DisplayAppRecovery.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ void DisplayApp::Process(void* instance) {
NRF_LOG_INFO("displayapp task started!");

// Send a dummy notification to unlock the lvgl display driver for the first iteration
xTaskNotifyGive(xTaskGetCurrentTaskHandle());
// xTaskNotifyGive(xTaskGetCurrentTaskHandle());

app->InitHw();
while (true) {
Expand Down Expand Up @@ -94,7 +94,7 @@ void DisplayApp::DisplayLogo(uint16_t color) {
Pinetime::Tools::RleDecoder rleDecoder(infinitime_nb, sizeof(infinitime_nb), color, colorBlack);
for (int i = 0; i < displayWidth; i++) {
rleDecoder.DecodeNext(displayBuffer, displayWidth * bytesPerPixel);
ulTaskNotifyTake(pdTRUE, 500);
// ulTaskNotifyTake(pdTRUE, 500);
lcd.DrawBuffer(0, i, displayWidth, 1, reinterpret_cast<const uint8_t*>(displayBuffer), displayWidth * bytesPerPixel);
}
}
Expand All @@ -103,7 +103,7 @@ void DisplayApp::DisplayOtaProgress(uint8_t percent, uint16_t color) {
const uint8_t barHeight = 20;
std::fill(displayBuffer, displayBuffer + (displayWidth * bytesPerPixel), color);
for (int i = 0; i < barHeight; i++) {
ulTaskNotifyTake(pdTRUE, 500);
// ulTaskNotifyTake(pdTRUE, 500);
uint16_t barWidth = std::min(static_cast<float>(percent) * 2.4f, static_cast<float>(displayWidth));
lcd.DrawBuffer(0, displayWidth - barHeight + i, barWidth, 1, reinterpret_cast<const uint8_t*>(displayBuffer), barWidth * bytesPerPixel);
}
Expand Down
4 changes: 2 additions & 2 deletions src/displayapp/LittleVgl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -245,7 +245,7 @@ void LittleVgl::StartTransitionAnimation() {
void LittleVgl::FlushDisplay(const lv_area_t* area, lv_color_t* color_p) {
uint16_t y1, y2, width, height = 0;

ulTaskNotifyTake(pdTRUE, 200);
// ulTaskNotifyTake(pdTRUE, 200);
// NOtification is still needed (even if there is a mutex on SPI) because of the DataCommand pin
// which cannot be set/clear during a transfert.

Expand All @@ -260,7 +260,7 @@ void LittleVgl::FlushDisplay(const lv_area_t* area, lv_color_t* color_p) {

if (height > 0) {
lcd.DrawBuffer(area->x1, y1, width, height, reinterpret_cast<const uint8_t*>(color_p), width * height * 2);
ulTaskNotifyTake(pdTRUE, 100);
// ulTaskNotifyTake(pdTRUE, 100);
}

uint16_t pixOffset = width * height;
Expand Down
4 changes: 2 additions & 2 deletions src/drivers/Spi.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ Spi::Spi(SpiMaster& spiMaster, uint8_t pinCsn) : spiMaster {spiMaster}, pinCsn {
nrf_gpio_pin_set(pinCsn);
}

bool Spi::Write(const uint8_t* data, size_t size) {
return spiMaster.Write(pinCsn, data, size);
bool Spi::Write(const uint8_t* data, size_t size, uint8_t pinLcdCmd, bool isData) {
return spiMaster.Write(pinCsn, data, size, pinLcdCmd, isData);
}

bool Spi::Read(uint8_t* cmd, size_t cmdSize, uint8_t* data, size_t dataSize) {
Expand Down
2 changes: 1 addition & 1 deletion src/drivers/Spi.h
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ namespace Pinetime {
Spi& operator=(Spi&&) = delete;

bool Init();
bool Write(const uint8_t* data, size_t size);
bool Write(const uint8_t* data, size_t size, uint8_t pinLcdCmd = -1, bool isLcdData = true);
bool Read(uint8_t* cmd, size_t cmdSize, uint8_t* data, size_t dataSize);
bool WriteCmdAndBuffer(const uint8_t* cmd, size_t cmdSize, const uint8_t* data, size_t dataSize);
void Sleep();
Expand Down
10 changes: 9 additions & 1 deletion src/drivers/SpiMaster.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ void SpiMaster::PrepareRx(const volatile uint32_t cmdAddress,
spiBaseAddress->EVENTS_END = 0;
}

bool SpiMaster::Write(uint8_t pinCsn, const uint8_t* data, size_t size) {
bool SpiMaster::Write(uint8_t pinCsn, const uint8_t* data, size_t size, uint8_t pinLcdCmd=-1, bool isLcdData = true) {
if (data == nullptr)
return false;
auto ok = xSemaphoreTake(mutex, portMAX_DELAY);
Expand All @@ -190,6 +190,14 @@ bool SpiMaster::Write(uint8_t pinCsn, const uint8_t* data, size_t size) {
} else {
DisableWorkaroundForFtpan58(spiBaseAddress, 0, 0);
}

if (pinLcdCmd >= 0){
if (isLcdData) {
nrf_gpio_pin_set(pinLcdCmd);
} else{
nrf_gpio_pin_clear(pinLcdCmd);
}
}

nrf_gpio_pin_clear(this->pinCsn);

Expand Down
2 changes: 1 addition & 1 deletion src/drivers/SpiMaster.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ namespace Pinetime {
SpiMaster& operator=(SpiMaster&&) = delete;

bool Init();
bool Write(uint8_t pinCsn, const uint8_t* data, size_t size);
bool Write(uint8_t pinCsn, const uint8_t* data, size_t size, uint8_t pinLcdCmd, bool isLcdData);
bool Read(uint8_t pinCsn, uint8_t* cmd, size_t cmdSize, uint8_t* data, size_t dataSize);

bool WriteCmdAndBuffer(uint8_t pinCsn, const uint8_t* cmd, size_t cmdSize, const uint8_t* data, size_t dataSize);
Expand Down
71 changes: 34 additions & 37 deletions src/drivers/St7789.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ void St7789::Init() {
SleepOut();
ColMod();
MemoryDataAccessControl();
VerticalScrollDefinition(0,320,0);
ColumnAddressSet();
RowAddressSet();
DisplayInversionOn();
Expand All @@ -27,17 +28,15 @@ void St7789::Init() {
}

void St7789::WriteCommand(uint8_t cmd) {
nrf_gpio_pin_clear(pinDataCommand);
WriteSpi(&cmd, 1);
spi.Write(&cmd, 1, pinDataCommand, false);
}

void St7789::WriteData(uint8_t data) {
nrf_gpio_pin_set(pinDataCommand);
WriteSpi(&data, 1);
void St7789::WriteDataByte(uint8_t data) {
spi.Write(&data, 1, pinDataCommand, true);
}

void St7789::WriteSpi(const uint8_t* data, size_t size) {
spi.Write(data, size);
void St7789::WriteData(const uint8_t* data, size_t size) {
spi.Write(data, size, pinDataCommand, true);
}

void St7789::SoftwareReset() {
Expand All @@ -55,29 +54,29 @@ void St7789::SleepIn() {

void St7789::ColMod() {
WriteCommand(static_cast<uint8_t>(Commands::ColMod));
WriteData(0x55);
WriteDataByte(0x55);
nrf_delay_ms(10);
}

void St7789::MemoryDataAccessControl() {
WriteCommand(static_cast<uint8_t>(Commands::MemoryDataAccessControl));
WriteData(0x00);
WriteDataByte(0x00);
}

void St7789::ColumnAddressSet() {
WriteCommand(static_cast<uint8_t>(Commands::ColumnAddressSet));
WriteData(0x00);
WriteData(0x00);
WriteData(Width >> 8u);
WriteData(Width & 0xffu);
WriteDataByte(0x00);
WriteDataByte(0x00);
WriteDataByte(Width >> 8u);
WriteDataByte(Width & 0xffu);
}

void St7789::RowAddressSet() {
WriteCommand(static_cast<uint8_t>(Commands::RowAddressSet));
WriteData(0x00);
WriteData(0x00);
WriteData(320u >> 8u);
WriteData(320u & 0xffu);
WriteDataByte(0x00);
WriteDataByte(0x00);
WriteDataByte(320u >> 8u);
WriteDataByte(320u & 0xffu);
}

void St7789::DisplayInversionOn() {
Expand All @@ -96,16 +95,16 @@ void St7789::DisplayOn() {

void St7789::SetAddrWindow(uint16_t x0, uint16_t y0, uint16_t x1, uint16_t y1) {
WriteCommand(static_cast<uint8_t>(Commands::ColumnAddressSet));
WriteData(x0 >> 8);
WriteData(x0 & 0xff);
WriteData(x1 >> 8);
WriteData(x1 & 0xff);
WriteDataByte(x0 >> 8);
WriteDataByte(x0 & 0xff);
WriteDataByte(x1 >> 8);
WriteDataByte(x1 & 0xff);

WriteCommand(static_cast<uint8_t>(Commands::RowAddressSet));
WriteData(y0 >> 8);
WriteData(y0 & 0xff);
WriteData(y1 >> 8);
WriteData(y1 & 0xff);
WriteDataByte(y0 >> 8);
WriteDataByte(y0 & 0xff);
WriteDataByte(y1 >> 8);
WriteDataByte(y1 & 0xff);

WriteToRam();
}
Expand All @@ -121,19 +120,19 @@ void St7789::DisplayOff() {

void St7789::VerticalScrollDefinition(uint16_t topFixedLines, uint16_t scrollLines, uint16_t bottomFixedLines) {
WriteCommand(static_cast<uint8_t>(Commands::VerticalScrollDefinition));
WriteData(topFixedLines >> 8u);
WriteData(topFixedLines & 0x00ffu);
WriteData(scrollLines >> 8u);
WriteData(scrollLines & 0x00ffu);
WriteData(bottomFixedLines >> 8u);
WriteData(bottomFixedLines & 0x00ffu);
WriteDataByte(topFixedLines >> 8u);
WriteDataByte(topFixedLines & 0x00ffu);
WriteDataByte(scrollLines >> 8u);
WriteDataByte(scrollLines & 0x00ffu);
WriteDataByte(bottomFixedLines >> 8u);
WriteDataByte(bottomFixedLines & 0x00ffu);
}

void St7789::VerticalScrollStartAddress(uint16_t line) {
verticalScrollingStartAddress = line;
WriteCommand(static_cast<uint8_t>(Commands::VerticalScrollStartAddress));
WriteData(line >> 8u);
WriteData(line & 0x00ffu);
WriteDataByte(line >> 8u);
WriteDataByte(line & 0x00ffu);
}

void St7789::Uninit() {
Expand All @@ -146,14 +145,12 @@ void St7789::DrawPixel(uint16_t x, uint16_t y, uint32_t color) {

SetAddrWindow(x, y, x + 1, y + 1);

nrf_gpio_pin_set(pinDataCommand);
WriteSpi(reinterpret_cast<const uint8_t*>(&color), 2);
WriteData(reinterpret_cast<const uint8_t*>(&color), 2);
}

void St7789::DrawBuffer(uint16_t x, uint16_t y, uint16_t width, uint16_t height, const uint8_t* data, size_t size) {
SetAddrWindow(x, y, x + width - 1, y + height - 1);
nrf_gpio_pin_set(pinDataCommand);
WriteSpi(data, size);
WriteData(data, size);
}

void St7789::HardwareReset() {
Expand Down
3 changes: 2 additions & 1 deletion src/drivers/St7789.h
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,8 @@ namespace Pinetime {
VerticalScrollStartAddress = 0x37,
ColMod = 0x3a,
};
void WriteData(uint8_t data);
void WriteData(const uint8_t* data, size_t s);
void WriteDataByte(uint8_t data);
void ColumnAddressSet();

static constexpr uint16_t Width = 240;
Expand Down
4 changes: 2 additions & 2 deletions src/recoveryLoader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ void DisplayLogo() {
Pinetime::Tools::RleDecoder rleDecoder(infinitime_nb, sizeof(infinitime_nb));
for (int i = 0; i < displayWidth; i++) {
rleDecoder.DecodeNext(displayBuffer, displayWidth * bytesPerPixel);
ulTaskNotifyTake(pdTRUE, 500);
// ulTaskNotifyTake(pdTRUE, 500);
lcd.DrawBuffer(0, i, displayWidth, 1, reinterpret_cast<const uint8_t*>(displayBuffer), displayWidth * bytesPerPixel);
}
}
Expand All @@ -133,7 +133,7 @@ void DisplayProgressBar(uint8_t percent, uint16_t color) {
static constexpr uint8_t barHeight = 20;
std::fill(displayBuffer, displayBuffer + (displayWidth * bytesPerPixel), color);
for (int i = 0; i < barHeight; i++) {
ulTaskNotifyTake(pdTRUE, 500);
// ulTaskNotifyTake(pdTRUE, 500);
uint16_t barWidth = std::min(static_cast<float>(percent) * 2.4f, static_cast<float>(displayWidth));
lcd.DrawBuffer(0, displayWidth - barHeight + i, barWidth, 1, reinterpret_cast<const uint8_t*>(displayBuffer), barWidth * bytesPerPixel);
}
Expand Down

0 comments on commit ce23767

Please sign in to comment.