Drivers for the ST7789 and ST7735 controllers

Of course. Just changing the rotation is enough to send random pixels to the whole screen:

DECLARE_DISPLAY(__Display);
DECLARE_LAYER(BackgroundLayer, 128, 160)
DECLARE_LAYER(BallLayer, 16, 16)
DECLARE_LAYER(TextLayer, 128, 50)

void AudioCallback(AudioHandle::InputBuffer in, AudioHandle::OutputBuffer out, size_t size)
{
	for (size_t i = 0; i < size; i++)
	{
		out[0][i] = in[0][i];
		out[1][i] = in[1][i];
	}
}

void setup()
{
	hw.Init();

	INIT_DISPLAY(__Display);
	__Display.setOrientation(Rotation::Degre_0);

	hw.SetAudioBlockSize(4); // number of samples handled per callback
	hw.SetAudioSampleRate(SaiHandle::Config::SampleRate::SAI_48KHZ);
	hw.StartAudio(AudioCallback);

}

int main(void)
{
	setup();

	DadGFX::cLayer *pBackground = ADD_LAYER(BackgroundLayer, 0, 0, 1);
	pBackground->drawFillRect(0, 0, 128, 160, DadGFX::sColor(9, 111, 148, 255));

	DadGFX::cLayer *pBall = ADD_LAYER(BallLayer, 0, 0, 10);
	pBall->drawFillCircle(7, 7, 7, DadGFX::sColor(255, 255, 255, 255));

	DadGFX::cImageLayer *pPenda = __Display.addLayer(Penda_map, 20, 10, 80, 80, 5);

	DadGFX::cFont Vanilla(&__Vanilla_Extract_20p);
	DadGFX::cLayer *pText = ADD_LAYER(TextLayer, 5, 5, 7);
	pText->setFont(&Vanilla);
	pText->setCursor(0, 0);
	pText->setTextFrontColor(DadGFX::sColor(245, 245, 245, 255));
	pText->drawText("Demo");
	pText->setCursor(0, Vanilla.getHeight());
	pText->drawText("Initializing... ");

	__Display.flush();

	float AvanceX = 7;
	float AvanceY = 5;
	int16_t PosX = 0;
	int16_t PosY = 100;

	while (1)
	{
		g_midi.run();

		PosX += AvanceX;
		if (PosX < 0)
		{
			PosX = 0;
			AvanceX = -AvanceX;
		}
		if (PosX >= TFT_HEIGHT - 30)
		{
			PosX = TFT_HEIGHT - 30;
			AvanceX = -AvanceX;
		}

		PosY += AvanceY;
		if (PosY < 0)
		{
			PosY = 0;
			AvanceY = -AvanceY;
		}

		if (PosY >= TFT_WIDTH - 7)
		{
			PosY = TFT_WIDTH - 7;
			AvanceY = -AvanceY;
		}

		pBall->moveLayer(PosX, PosY);

		__Display.flush();
		daisy::System::Delay(10);
	}
}

Hello Marcel,

You need to modify UserConfig.h:

//-------------------------------------------------------------------------  
// Screen dimensions in pixels  
#define TFT_WIDTH       128       // Screen width in pixels  
#define TFT_HEIGHT      160       // Screen height in pixels  

Here is a working code on my side:

DadGFX::cLayer* pBackground90 = ADD_LAYER(BackgroundLayer90, 0, 0, 0);  
DadGFX::cLayer* pBackground0 = ADD_LAYER(BackgroundLayer0, 0, 0, 0);  
pBackground90->drawFillRect(0, 0, 160, 128, DadGFX::sColor(0, 200, 200, 255));  
pBackground0->drawFillRect(0, 0, 128, 160, DadGFX::sColor(200, 0, 200, 255));  
__Display.addLayer(Penda_map, 20, 10, 80, 80, 8);  

while (1) {  
    __Display.setOrientation(Rotation::Degre_0);  
    pBackground0->changeZOrder(1);  
    pBackground90->changeZOrder(0);  
    __Display.flush();  
    HAL_Delay(1000);  

    __Display.setOrientation(Rotation::Degre_90);  
    pBackground0->changeZOrder(0);  
    pBackground90->changeZOrder(1);  
    __Display.flush();  
    HAL_Delay(1000);  

    __Display.setOrientation(Rotation::Degre_180);  
    pBackground0->changeZOrder(1);  
    pBackground90->changeZOrder(0);  
    __Display.flush();  
    HAL_Delay(1000);  

    __Display.setOrientation(Rotation::Degre_270);  
    pBackground0->changeZOrder(0);  
    pBackground90->changeZOrder(1);  
    __Display.flush();  
    HAL_Delay(1000);  
}

ST7735

Philippe

The dimensions in UserConfig were already like you posted. So did not touch them (they are already in portrait mode, as in width is smaller then height, even though it works correctly in landscape only, which is odd).
Copied your code (assumed the layer declarations) but it remains in landscape.
If i put debug output between the orientations changes i only get one. So it appears to be crashing…

When I actually do switch the dimensions in UserConfig.h to:

#define TFT_WIDTH       160 // Screen width in pixels  
#define TFT_HEIGHT      128 // Screen height in pixels 

It actually does not crash any more.
But I get:
9mhxvn

It appears to be some memory corruption perhaps.
Been looking at the MADCTL register. But I can spot no obvious errors. Not unless you cache the access points somewhere perhaps…

Ill see if I can attach a debugger.

Actually appeared the debugger scared if off.
It’s not crashing any more.
Suspecting that might have something to do with timing and flushing.
There are still bands (rects really) however that seem to be out of reach…
9mi5h1

Edit:

Actually I have been able to provoke the crash (that was presumably what was happening when I saw the garbled screen earlier).
It appears to happen when flushing after setting it to Degre_0 at this position:

i get an exception:

#define  SCB_CFSR_IMPRECISERR                ((uint32_t)0x00000400)        /*!< Imprecise data bus error */

Maybe reduce the number of blocks.:

#define NB_BLOC_WIDTH 8 // Number of blocks horizontally
#define NB_BLOC_HEIGHT 8 // Number of blocks vertically

Reduce the speed to ensure there are no SPI transmission errors.
#define TFT_SPI_BaudPrescaler PS_8 // SPI baud rate prescaler

Changing the bloc size did the trick!
At 8 x 8 it works well. The speed does not matter as much.

Ill keep on experimenting. Thanks for the help!

Hello,
There is indeed a bug that appears when the number of vertical blocks is different from the number of horizontal blocks. I will fix this issue, but it is not trivial.
Thank you for helping me discover this problem and thus improve the reliability of the driver.
Philippe

Hello,
The bug is fixed on GitHub.
Philippe

1 Like

Thanks! Just pulled.

Have you btw ever considered making it compatible with the libDaisy UI library?

Was thinking about making an oled_color_display wrapper, in stead of rolling my own UI framework…

1 Like

This is something I was working on as well, haven’t made much progress, I was doing that and changing the color formatting from RGB to HSV, just to make it easier to cycle through colors