Forum: Projekte & Code FT800 / FT810 Library


Beitrag #6091190 wurde von einem Moderator gelöscht.
von Rudolph R. (rudolph)


Lesenswert?

Happy new year everyone! :-)

I am still interested in expanding the supported platforms and so I have 
added GD32VF103 for RISC-V a couple of days ago.
I have not tested it though (yet), as that would require me to solder 
jumper wires to my Longan Nano.

Since the GD21VF103 is "just" a GD32F103 with a RISC-C core, basic 
support for STM32 should be almost implemented now as well.
Well, apart from DMA that is.

If you would like to see other controllers added, tell me which.
And if you already have implemented the support code for a different 
controller, please post it.

And to keep things interesting, Bridgetek and FTDI posted news in 
november that they will be showing BT817 at Embedded World in february.

I have no solid idea so far what they are up to, but I will stay on top 
of it and add whatever new registers, defines and/or functions the BT817 
may require to unlock its added functionality.

von M. B. (mokkka)


Lesenswert?

Hallo Rudolph,

erstmal vielen Dank für die Bibliothek, die Arbeit die du da rein 
steckst und  den Support den du hier gibst.

Ich habe den FT800 mit einem 4,3" Resistiven Touchdisplay an ein STM32 
Chip angeschlossen. Die Kommunikation mit dem FT800 funktioniert und ich 
kann auch Elemente auf dem Display anzeigen.

Nun habe ich folgendes Problem:

Im ersten Schritt habe ich das Beispielprojekt von GitHub genommen und 
den Teil zur Kalibrierung im tft.c File aktiviert. Die Werte werden mir 
angezeigt und ich habe sie in einen eigenen define-Block übernommen.

Danach habe ich mit dem unteren Programmteil eine neue Displayliste 
erzeugt und mir einen Button anzeigen zu lassen.
1
  EVE_cmd_dl(CMD_DLSTART);
2
  EVE_cmd_dl(CLEAR_COLOR_RGB(31, 63, 127));
3
  EVE_cmd_dl(CLEAR(1,1,1));
4
  EVE_cmd_text(240, 68, 27, EVE_OPT_CENTER, "Test Text!!");
5
  EVE_cmd_dl(TAG_MASK(1));
6
  EVE_cmd_dl(TAG(5));
7
  EVE_cmd_button(180, 120, 120, 36, 27, EVE_OPT_CENTER, "Test Button!!");
8
  EVE_cmd_dl(DL_DISPLAY);
9
  EVE_cmd_dl(CMD_SWAP);
10
  EVE_cmd_execute();

Das alles geschieht vor dem while(1)-Block in der main-Routine.

Im while(1)-Block polle ich das REG_TOUCH_TAG-Register und gebe das 
Touch-Tag mit Hilfe von UART über Putty aus.

Beim Berühren des Buttons auf dem Display wird aber weiterhin eine 0 
ausgegeben bzw. wenn ich wahrlos auf dem Display neben dem Button drücke 
erscheint manchmal die erwartete 5 manchmal die 0.

Ich hab dann wieder die Kalibrierung durchgeführt und siehe da, es 
kommen andere Werte heraus.

Jetzt ist die Frage, ob man eine Kalibrierung jedes mal beim Start 
ausführen muss und die Kalibrierungsdaten ändern sich oder ob ich 
einfach ein Montagsprodukt erwischt habe und meine Toucheinheit einen 
Schuss weg hat.

Danke schonmal im Vorraus!

Gruß
Moritz

von Rudolph R. (rudolph)


Lesenswert?

Hallo,

ich will nicht ausschliessen, dass ich gerade was kaputt gemacht habe, 
ich muss mir das noch genauer ansehen.

Aber benutzt mal einen anderen TAG Wert ab 10 aufwärts, da drunter ist 
das bei mir gerade nicht so richtig stabil.
Bei 5 schwankt der Wert komischerweise die ganze Zeit zwischen 4 und 5.
Bei 9 zwischen 8 und 9.
Bei 1 zwischen 0 und 1.
2, 3, 4, 6, 7, 8, 11, 15 und 19 funktionieren - was auch immer da los 
ist.

Zumindest stelle ich das gerade mit meinem EVE3-43G fest, wobei ich mir 
die Werte anzeigen lasse.

Meine FT800 Displays bekomme ich spontan nicht reaktiviert, die sind 
schon länger nicht mehr so wirklich interessant. :-)

Das TAG_MASK habe ich auch noch nie vewendet, das bewirkt so auch nichts 
da "1" sowieso der Default Wert ist.

Ich setze einfach ein TAG(0) für kein Touch, obwohl ohne einen Tag Wert 
zu setzen erstmal 255 geliefert wird.
Aber wenn kein Touch erkannt wird ist der Wert eben auch Null.

M. B. schrieb:
> Ich habe den FT800 mit einem 4,3" Resistiven Touchdisplay

Welches?

> an ein STM32 Chip angeschlossen.

Welchen und magst Du mal den Code dafür posten?


Was die Kalibrierung angeht, die mache ich in der Regel für jedes 
Display nur einmal und bisher passt es meistens sogar für verschiedene 
Displays vom gleichen Typ.
Wichtig ist allerdings, dass man die Kalibrierung präzise ausführt.
Bei resistiv geht das ja mit irgeneinem feinen aber stumpfen Gegenstand.
Für meine kapazitiven Displays habe ich mir extra Eingabestifte gekauft 
um die Punkte besser treffen zu können.

Und beim Spielen mit dem Stift auf dem Button habe ich gerade 
festgestellt, dass meine aktuellen Kalibrierwerte einen leichten Versatz 
nach Rechts haben, die Werte sind okay, das geht aber noch besser.

von M. B. (mokkka)


Lesenswert?

> Aber benutzt mal einen anderen TAG Wert ab 10 aufwärts, da drunter ist
> das bei mir gerade nicht so richtig stabil.
> Bei 5 schwankt der Wert komischerweise die ganze Zeit zwischen 4 und 5.
> Bei 9 zwischen 8 und 9.
> Bei 1 zwischen 0 und 1.
> 2, 3, 4, 6, 7, 8, 11, 15 und 19 funktionieren - was auch immer da los
> ist.

Ok implementiert und keine Besserung immernoch wird nur der Wert 0 
ausgegeben

> M. B. schrieb:
>> Ich habe den FT800 mit einem 4,3" Resistiven Touchdisplay
>
> Welches?

ConnectEVE der Firma mikroE. Display ist schwer herauszufinden ich habe 
vorne noch einen Schriftzug mit RXA-043005 das ist allerdings nur die 
Bezeichnung vom Touchpanel. Zum TFT habe ich gar nichts gefunden.

>> an ein STM32 Chip angeschlossen.
>
> Welchen und magst Du mal den Code dafür posten?

STM32F407VG

Das ist die main() ohne Initialisierung der ganzen Schnittstellen welche 
automatisch generiert werden
1
  /* USER CODE BEGIN 2 */ 
2
  LL_SPI_Enable(SPI1);
3
4
  TFT_init();
5
6
  EVE_cmd_dl(CMD_DLSTART);
7
  EVE_cmd_dl(CLEAR_COLOR_RGB(31, 63, 127));
8
  EVE_cmd_dl(CLEAR(1,1,1));
9
  EVE_cmd_dl(TAG(0));
10
  EVE_cmd_text(240, 68, 27, EVE_OPT_CENTER, "Test Text!!");
11
  EVE_cmd_dl(TAG(10));
12
  EVE_cmd_button(180, 120, 120, 36, 27, 0, "Test Button!!");
13
  EVE_cmd_dl(DL_DISPLAY);
14
  EVE_cmd_dl(CMD_SWAP);
15
  EVE_cmd_execute();
16
17
  /* USER CODE END 2 */
18
 
19
 
20
21
  /* Infinite loop */
22
  /* USER CODE BEGIN WHILE */
23
  while (1)
24
  {
25
    /* USER CODE END WHILE */
26
27
    /* USER CODE BEGIN 3 */
28
   touch_tag=EVE_memRead8(REG_TOUCH_TAG);
29
   //if (touch_tag>0){
30
     if(touch_tag>9){
31
       touch_tag_uart[1]=(touch_tag%10)+48; //zehner Stelle als ASCII
32
       touch_tag_uart[0]=(touch_tag/10)+48; //einer Stelle als ASCII
33
     } else {
34
       touch_tag_uart[0]=32; // ASCII Space
35
       touch_tag_uart[1]=touch_tag+48;
36
     }
37
     HAL_UART_Transmit_IT(&huart2, touch_tag_uart, 4);
38
     while(HAL_UART_GetState(&huart2)!=HAL_UART_STATE_READY);
39
     touch_tag=0;
40
      //}
41
  }
42
  /* USER CODE END 3 */

Das ist der Teil aus der target.h
1
#if defined (STM32F407xx)
2
3
#include "EVE_config.h"
4
#include "main.h"
5
6
  static inline void EVE_pdn_clear(void)
7
  {
8
    HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_SET);
9
  }
10
11
  static inline void EVE_pdn_set(void)
12
  {
13
    HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_RESET);
14
  }
15
  static inline void EVE_cs_clear(void)
16
  {
17
    HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_SET);
18
  }
19
20
  static inline void EVE_cs_set(void)
21
  {
22
    HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_RESET);
23
  }
24
25
  static inline void spi_transmit(uint8_t byte)
26
  {
27
       while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
28
       LL_SPI_TransmitData8(EVE_SPI, byte);
29
30
       while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
31
                 LL_SPI_ReceiveData8(EVE_SPI);
32
  }
33
34
  static inline uint8_t spi_receive(uint8_t byte)
35
  {
36
       while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
37
       LL_SPI_TransmitData8(EVE_SPI, byte);
38
39
       while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
40
                 return LL_SPI_ReceiveData8(EVE_SPI);
41
  }
42
43
  static inline void spi_transmit_async(uint8_t byte)
44
  {
45
    #if EVE_DMA
46
        //TODO dma implementieren
47
    #else
48
49
    while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
50
       LL_SPI_TransmitData8(EVE_SPI, byte);
51
52
       while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
53
                 LL_SPI_ReceiveData8(EVE_SPI);
54
55
    #endif
56
  }
57
58
  static inline uint8_t spi_receive_async(uint8_t byte)
59
  {
60
    #if EVE_DMA
61
        //TODO dma implementieren
62
    #else
63
64
    while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
65
       LL_SPI_TransmitData8(EVE_SPI, byte);
66
67
       while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
68
                 return LL_SPI_ReceiveData8(EVE_SPI);
69
70
    #endif
71
  }
72
73
  static inline void DELAY_MS(uint32_t delay)
74
  {
75
    HAL_Delay(delay);
76
  }
77
78
    static inline uint8_t fetch_flash_byte(const uint8_t *data)
79
    {
80
        return *data;
81
    }
82
83
#endif


> Was die Kalibrierung angeht, die mache ich in der Regel für jedes
> Display nur einmal und bisher passt es meistens sogar für verschiedene
> Displays vom gleichen Typ.
> Wichtig ist allerdings, dass man die Kalibrierung präzise ausführt.
> Bei resistiv geht das ja mit irgeneinem feinen aber stumpfen Gegenstand.
> Für meine kapazitiven Displays habe ich mir extra Eingabestifte gekauft
> um die Punkte besser treffen zu können.
>
> Und beim Spielen mit dem Stift auf dem Button habe ich gerade
> festgestellt, dass meine aktuellen Kalibrierwerte einen leichten Versatz
> nach Rechts haben, die Werte sind okay, das geht aber noch besser.

Ja ein bisschen nach rechts oder links finde ich in Ordnung allerdings 
weichen die Werte schon sehr stark ab.

z.B.:
1
                         1.Durchlauf     2.Durchlauf     3.Durchlauf     
2
3
TOUCH_TRANSFORM_A:          98982 UL        33658 UL        33536 UL
4
TOUCH_TRANSFORM_B:            158 UL        65690 UL   4294966582 UL
5
TOUCH_TRANSFORM_C:     4293468776 UL   4276760870 UL   4294069736 UL 
6
TOUCH_TRANSFORM_D:     4294966920 UL   4294966974 UL   4294966694 UL
7
TOUCH_TRANSFORM_E:          20348 UL        20404 UL        86052 UL
8
TOUCH_TRANSFORM_F:     4293312168 UL   4293521822 UL   4276733650 UL

Daher die Überlegung dass das Panel nicht ganz in Ordnung ist.

von Rudolph R. (rudolph)


Lesenswert?

M. B. schrieb:
>> Aber benutzt mal einen anderen TAG Wert ab 10 aufwärts, da drunter ist
>> das bei mir gerade nicht so richtig stabil.
>
> Ok implementiert und keine Besserung immernoch wird nur der Wert 0
> ausgegeben

Seltsam.

> ConnectEVE der Firma mikroE. Display ist schwer herauszufinden ich habe
> vorne noch einen Schriftzug mit RXA-043005 das ist allerdings nur die
> Bezeichnung vom Touchpanel. Zum TFT habe ich gar nichts gefunden.

Das ist schon etwas schwer angestaubt soweit. :-)
Ich hoffe das hast Du nicht gerade erst zu dem auf Mouser immer noch 
angezeigtem Kurs von 62 Euro gekauft.
Es gibt Beispielcode von MikroElektronika und da sind die Parameter 
drin, das habe ich gerade mal verglichen und ein Profil dafür 
hinzugefügt.
1
/* untested */
2
/* MikroElektronika ConnectEVE, FT800 480x272 4.3" */
3
#if defined (EVE_CONNECTEVE)
4
#define EVE_HSIZE  (480L)
5
#define EVE_VSIZE  (272L)
6
7
#define EVE_VSYNC0  (0L)
8
#define EVE_VSYNC1  (10L)
9
#define EVE_VOFFSET  (12L)
10
#define EVE_VCYCLE  (286L)
11
#define EVE_HSYNC0  (0L)
12
#define EVE_HSYNC1  (41L)
13
#define EVE_HOFFSET  (43L)
14
#define EVE_HCYCLE   (525L)
15
#define EVE_PCLKPOL  (1L)
16
#define EVE_SWIZZLE  (0L)
17
#define EVE_PCLK  (5L)
18
#define EVE_CSPREAD  (0L)
19
#define EVE_TOUCH_RZTHRESH (2000L)
20
#define EVE_HAS_CRYSTAL
21
#endif

Die Parameter sind fast die gleichen wie bei den anderen 4.3" Displays.
Seltsamerweise weichen die Werte für VCYCLE and HCYCLE ab.

Das einzubauen und dafür zu compilieren hat auf jeden Fall noch einen 
Bug in EVE_get_touch_tag() aufgedeckt - die FT80x haben ja nur ein 
TOUCH_TAG Register...

> STM32F407VG

Ah okay, das ist schon eine ordentlich fixe Kachel. :-)

> touch_tag=EVE_memRead8(REG_TOUCH_TAG);
>    //if (touch_tag>0){
>      if(touch_tag>9){
>        touch_tag_uart[1]=(touch_tag%10)+48; //zehner Stelle als ASCII
>        touch_tag_uart[0]=(touch_tag/10)+48; //einer Stelle als ASCII
>      } else {
>        touch_tag_uart[0]=32; // ASCII Space
>        touch_tag_uart[1]=touch_tag+48;
>      }
>      HAL_UART_Transmit_IT(&huart2, touch_tag_uart, 4);
>      while(HAL_UART_GetState(&huart2)!=HAL_UART_STATE_READY);
>      touch_tag=0;

Auf den ersten Blick finde ich da nichts.
Du könntest mal REG_TOUCH_SCREEN_XY lesen und per sprintf() in einen 
String werfen, am besten als Hex-Wert.

M. B. schrieb:
> Das ist der Teil aus der target.h
...

Danke, ich schaue mal das ich das einbaue.
Wie sehen die Defines für EVE_PDN und EVE_CS und EVE_SPI aus?

Und die Includes passen nicht so richtig, EVE_config.h sollte nicht 
gebraucht werden und die main.c sollte eher die EVE_target.h inkludieren 
anstatt anders herum.
Statt dessen sollte da eher nur #include "stm32f4xx.h" stehen.

Die HAL Funktionen dürften das ganze übrigens nicht nur aufblähen, die 
sind auch verhältnismäßig langsam.
Die haben das gleiche Problem wie z.B. digitalWrite() beim Arduino, 
überflüssigerweise wird zur Laufzeit ermittelt was man eigentlich tun 
will.
Immer und immer wieder.
Zusätzlich fängt man sich mit dem Funktionsaufruf auch noch eigentlich 
überflüssige Stack-Zugriffe ein, was noch mehr Zeit kostet.

Daher benutzen meine AVR und ATSAM Funktionen direkte Register-Zugriffe.
Alleine den Funkions-Aufruf zu vermeiden macht das messbar schneller.

In den spi_transmit Funktionen LL_SPI_ReceiveData8(EVE_SPI); aufzurufen 
macht das ganze dann noch mal extra langsam.

> Ja ein bisschen nach rechts oder links finde ich in Ordnung allerdings
> weichen die Werte schon sehr stark ab.
>
> z.B.:                         1.Durchlauf     2.Durchlauf
> 3.Durchlauf
>
> TOUCH_TRANSFORM_A:          98982 UL        33658 UL        33536 UL
> TOUCH_TRANSFORM_B:            158 UL        65690 UL   4294966582 UL
> TOUCH_TRANSFORM_C:     4293468776 UL   4276760870 UL   4294069736 UL
> TOUCH_TRANSFORM_D:     4294966920 UL   4294966974 UL   4294966694 UL
> TOUCH_TRANSFORM_E:          20348 UL        20404 UL        86052 UL
> TOUCH_TRANSFORM_F:     4293312168 UL   4293521822 UL   4276733650 UL

Och, die Werte weichen bei mir auch immer mehr oder weniger stark ab, 
egal wie oft ich das neu kalibriere.
Richtig erklären kann ich das auch nicht, das liegt erstmal auch daran 
wie diese Werte verwendet werden.

Du kannst Dir ja mal die Funktion EVE_calibrate_manual() ansehen.
Da sieht man wie sich die Werte ergeben.
Da das aber auch nur bestenfalls die Hälfte des Puzzles ist, habe ich 
mich lieber was anderem gewidmet als bis ins Detail zu verstehen wie das 
funktioniert. :-)

: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

Ich habs mal eingebaut und dabei beschleunigt:
1
    #if defined (STM32F407xx)
2
    
3
    #include "stm32f4xx.h"
4
5
    #define EVE_CS_PORT GPIOD
6
    #define EVE_CS GPIO_PIN_12
7
    #define EVE_PDN_PORT GPIOD
8
    #define EVE_PDN GPIO_PIN_13
9
    #define EVE_SPI SPI1
10
    
11
    #define DELAY_MS(ms) HAL_Delay(ms)
12
      
13
    static inline void EVE_pdn_clear(void)
14
    {
15
      EVE_PDN_PORT->BSRR = EVE_PDN;
16
//      HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_SET);
17
    }
18
19
    static inline void EVE_pdn_set(void)
20
    {
21
      EVE_PDN_PORT->BSRR = (uint32) EVE_PDN << 16;
22
//      HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_RESET);
23
    }
24
25
    static inline void EVE_cs_clear(void)
26
    {
27
      EVE_CS_PORT->BSRR = EVE_CS;
28
//      HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_SET);
29
    }
30
31
    static inline void EVE_cs_set(void)
32
    {
33
      EVE_CS_PORT->BSRR = (uint32) EVE_CS << 16;
34
//      HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_RESET);
35
    }
36
37
    static inline void spi_transmit(uint8_t byte)
38
    {
39
      EVE_SPI->DR = byte;
40
      while((EVE_SPI->SR & SPI_SR_TXE) == 0);
41
    }
42
43
    static inline void spi_transmit_async(uint8_t byte)
44
    {
45
      #if EVE_DMA
46
        EVE_dma_buffer[EVE_dma_buffer_index++] = data;
47
      #else
48
        EVE_SPI->DR = byte;
49
        while((EVE_SPI->SR & SPI_SR_TXE) == 0);
50
      #endif
51
    }
52
53
    static inline uint8_t spi_receive(uint8_t byte)
54
    {
55
      EVE_SPI->DR = byte;
56
      while((EVE_SPI->SR & SPI_SR_TXE) == 0);
57
      while((EVE_SPI->SR & SPI_SR_RXE) == 0); /* does most likely nothing */
58
      return EVE_SPI->DR;
59
    }
60
61
    static inline uint8_t fetch_flash_byte(const uint8_t *data)
62
    {
63
      return *data;
64
    }
65
66
    #endif  /* STM32F407xx */

Ich kann das nicht bauen, ich habe mir jetzt nur mal angesehen was im 
STM32F407 Referenz-Manual so steht und was der STM32F4xx_HAL_Driver so 
treibt.

Und natürlich sind die Defines für die Ports und die Pins frei erfunden. 
:-)

Edit: okay, die Optimierung für den PowerDown Pin ist eher überflüssig, 
das wird ja kaum mal verwendet.

Edit2: das Define für DELAY_MS war falsch..

: Bearbeitet durch User
von M. B. (mokkka)


Lesenswert?

Rudolph R. schrieb:
> Und die Includes passen nicht so richtig, EVE_config.h sollte nicht
> gebraucht werden und die main.c sollte eher die EVE_target.h inkludieren
> anstatt anders herum.
> Statt dessen sollte da eher nur #include "stm32f4xx.h" stehen.

Ich benutze die CubeMX Oberfläche um den Chip zu initialisieren. Die 
kreiert defines in der main.h. Diese defines habe ich in der config.h 
umdefiniert damit man nur an die config.h und nicht immer wieder an die 
target.h heranmuss.

Rudolph R. schrieb:
> Ich habs mal eingebaut und dabei beschleunigt:

Ich hab einen neuen pull gemacht und es sind noch ein paar Probleme 
aufgetaucht.

Rudolph R. schrieb:
1
static inline void spi_transmit(uint8_t byte)
2
     {
3
       EVE_SPI->DR = byte;
4
       while((EVE_SPI->SR & SPI_SR_TXE) == 0);
5
     }
6
 
7
     static inline void spi_transmit_async(uint8_t byte)
8
     {
9
       #if EVE_DMA
10
         EVE_dma_buffer[EVE_dma_buffer_index++] = data;
11
       #else
12
         EVE_SPI->DR = byte;
13
         while((EVE_SPI->SR & SPI_SR_TXE) == 0);
14
       #endif
15
     }
16
 
17
     static inline uint8_t spi_receive(uint8_t byte)
18
     {
19
       EVE_SPI->DR = byte;
20
       while((EVE_SPI->SR & SPI_SR_TXE) == 0);
21
       while((EVE_SPI->SR & SPI_SR_RXE) == 0); /* does most likely 
22
 nothing */
23
       return EVE_SPI->DR;
24
     }

Soweit ich das verstanden habe wird der Indikator SPI_SR_TXE gesetzt, 
wenn das Byte aus SPI*_DR erfolgreich in den Transmit Buffer geschrieben 
wurde. Deshalb hatte ich das vor dem Schreiben in das SPI*_DR Register 
abgefragt. Ich habe es mal mit beiden Versionen versucht also vor und 
nach dem Schreiben in das DR-Register. Ich konnte jetzt keinen 
Unterschied feststellen.

Der zweite Indikator heißt SPI_SR_RXNE.

Das zweite Problem entstand in der EVE_commands.h. Ich weiß nicht wie es 
bei anderen MCUs ist allerdings musste ich für den STM32F4 zusätzlich 
inttypes.h einbinden.

Nach diesen Änderungen, konnte ich die Bibliothek kompilieren. Trotzdem 
läuft es nicht und ich bekomme bei einem Read keine anständigen Werte 
zurück. Nach meiner Vermutung liegt das daran dass der Chip zu schnell 
für den FT800 ist. Durch Delays konnte ich das Display kurzzeitig zum 
Laufen kriegen. Nach einer Kalibrierung funktionierte es aber wieder 
nicht. Mit den LL-Bibliotheken funktioniert es weiterhin.

Rudolph R. schrieb:
> In den spi_transmit Funktionen LL_SPI_ReceiveData8(EVE_SPI); aufzurufen
> macht das ganze dann noch mal extra langsam

Meinst du damit den Aufruf von mehreren Funktionen? Im Grunde macht die 
Funktion ja nichts anderes als den Register auszugeben bzw beim Transmit 
das Register mit einem Pointer zu verbinden und mit dem dann die Daten 
über den Pointer in das Register zu schreiben. Bringt das soviel 
Overhead?
1
__STATIC_INLINE uint8_t LL_SPI_ReceiveData8(SPI_TypeDef *SPIx)
2
{
3
  return (uint8_t)(READ_REG(SPIx->DR));
4
}
1
__STATIC_INLINE void LL_SPI_TransmitData8(SPI_TypeDef *SPIx, uint8_t TxData)
2
{
3
#if defined (__GNUC__)
4
  __IO uint8_t *spidr = ((__IO uint8_t *)&SPIx->DR);
5
  *spidr = TxData;
6
#else
7
  *((__IO uint8_t *)&SPIx->DR) = TxData;
8
#endif /* __GNUC__ */
9
}

: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

M. B. schrieb:
> Rudolph R. schrieb:
>> Und die Includes passen nicht so richtig, EVE_config.h sollte nicht
>> gebraucht werden und die main.c sollte eher die EVE_target.h inkludieren
>> anstatt anders herum.
>> Statt dessen sollte da eher nur #include "stm32f4xx.h" stehen.
>
> Ich benutze die CubeMX Oberfläche um den Chip zu initialisieren. Die
> kreiert defines in der main.h. Diese defines habe ich in der config.h
> umdefiniert damit man nur an die config.h und nicht immer wieder an die
> target.h heranmuss.

Wenn Du Dir mal mein (veraltetes, okay) Beispiel ansiehst, da gibt es 
noch eine "tft.c" und eine "tft.h".

Da habe ich die High-Level Funktionen drin die von der main.c aus
aufgerufen werden, modular und so.

Die "tft.h" exportiert bei mir aktuell:

extern uint16_t num_profile_a, num_profile_b;

void TFT_init(void);
void TFT_touch(void);
void TFT_display(void);

Die beiden Zahlenwerte beschreibe ich in der Hauptschleife, dazu messe 
ich mit einem Timer wie lange die TFT_touch() und die TFT_display() 
jeweils zur Ausführung benötigen.

Die "tft.c" includiert:
#include "EVE.h"
#include "EVE_target.h"
#include "EVE_commands.h"
#include "tft_data.h"

Da nun die "EVE_target.h" wiederrum die Platform-spezifischen Includes 
einfügt ist die tft.c als solche mit jeder Plattform benutzbar.

Packt man das alles in die main.c greift das natürlich soweit nicht, da 
die main.c quasi zwindend Plattform-spezifisch ist.

Also klar, mach doch, aber das ist ein wenig anders gemeint. :-)

> Soweit ich das verstanden habe wird der Indikator SPI_SR_TXE gesetzt,
> wenn das Byte aus SPI*_DR erfolgreich in den Transmit Buffer geschrieben
> wurde. Deshalb hatte ich das vor dem Schreiben in das SPI*_DR Register
> abgefragt. Ich habe es mal mit beiden Versionen versucht also vor und
> nach dem Schreiben in das DR-Register. Ich konnte jetzt keinen
> Unterschied feststellen.

Die einfachste Anwort ist erstmal, ich mache das überall so, für jede 
Plattform, schreiben, dann warten das der Transfer durch ist.
Damit ist zum Beispiel sichergestellt, dass das Chip-Select nicht zu 
früh wieder hoch gezogen wird und der SPI kann immer Daten annehmen.
Natürlich kann man das auch anderes herum machen und erstmal testen ob 
der SPI bereit ist Daten anzunehmen, da ich das aber nirgendwo sonst 
gemacht habe, ist es anders herum konsistenter.

> Der zweite Indikator heißt SPI_SR_RXNE.

Ups, das kommt davon wenn man das nicht compiliert.

Ich muss mal schauen ob ich irgendwoher ein STM32F407 Projekt bekomme 
das ich mit PlatformIO bauen kann.

Im Datenblatt ist mir dann noch was aufgefallen, die reinen Schreiben 
Funktionen sollten besser noch das RXNE Flag löschen.
Das ist vielleicht nicht ganz so fatal wie bei den ATSAM, aber wenn man 
Lesen und Schreiben auf dem SPI aktiv hat gibt es sonst einen Überlauf.
1
    static inline void spi_transmit(uint8_t byte)
2
    {
3
      EVE_SPI->DR = byte;
4
      while((EVE_SPI->SR & SPI_SR_TXE) == 0);
5
      (void) EVE_SPI->DR; /* dummy read-access to clear SPI_SR_RXNE */
6
    }
7
8
    static inline void spi_transmit_async(uint8_t byte)
9
    {
10
      #if EVE_DMA
11
        EVE_dma_buffer[EVE_dma_buffer_index++] = data;
12
      #else
13
        EVE_SPI->DR = byte;
14
        while((EVE_SPI->SR & SPI_SR_TXE) == 0);
15
        (void) EVE_SPI->DR; /* dummy read-access to clear SPI_SR_RXNE */
16
      #endif
17
    }
18
19
    static inline uint8_t spi_receive(uint8_t byte)
20
    {
21
      EVE_SPI->DR = byte;
22
      while((EVE_SPI->SR & SPI_SR_TXE) == 0);
23
      while((EVE_SPI->SR & SPI_SR_RXNE) == 0); /* does most likely nothing */
24
      return EVE_SPI->DR;
25
    }

> Das zweite Problem entstand in der EVE_commands.h. Ich weiß nicht wie es
> bei anderen MCUs ist allerdings musste ich für den STM32F4 zusätzlich
> inttypes.h einbinden.

Da die EVE_commands.c die EVE_target.h includiert wird damit implizit 
oder explizit auch die stdint.h mit includiert.
Für AVR, ATSAM, RISC-V und auch STM32 passiert das automatisch über die 
System-Includes.
#include "stm32f4xx.h" -> #include "stm32f407xx.h" -> #include 
<stdint.h>

> Trotzdem läuft es nicht und ich bekomme bei einem Read
> keine anständigen Werte zurück.

Oh, vielleicht habe ich das gerade schon gefixt mit dem Löschen von RXNE 
bei den Schreib-Funktionen.

> Nach meiner Vermutung liegt das daran dass der Chip zu schnell
> für den FT800 ist.

Das sollte eigentlich so gut wie nicht passieren können.

> Durch Delays konnte ich das Display kurzzeitig zum
> Laufen kriegen.

Delays an welcher Stelle?
Wie schnell hast Du den SPI laufen? Zumindest für das Init sollte das 
unter 11MHz sein, dann unter 30MHz wobei die Hardware das auch mit 
machen muss.

Wenn Du einen Logik-Analyzer hast, zieh doch mal einen Trace.

>> In den spi_transmit Funktionen LL_SPI_ReceiveData8(EVE_SPI); aufzurufen
>> macht das ganze dann noch mal extra langsam
>
> Meinst du damit den Aufruf von mehreren Funktionen? Im Grunde macht die
> Funktion ja nichts anderes als den Register auszugeben bzw beim Transmit
> das Register mit einem Pointer zu verbinden und mit dem dann die Daten
> über den Pointer in das Register zu schreiben. Bringt das soviel
> Overhead?
> __STATIC_INLINE uint8_t LL_SPI_ReceiveData8(SPI_TypeDef *SPIx)
> {
>   return (uint8_t)(READ_REG(SPIx->DR));
> }

In dem besonderen Fall macht es überhaupt keinen Unterschied,
da LL_SPI_ReceiveData8() als STATIC INLINE definiert ist, genau wie die 
Funktionen in der EVE_target.h.
Das ergibt überhaupt keinen Overhead da kein Funktionsaufruf statt 
findet.

Nett, das habe ich schon ganz anders gesehen.
Hilft halt echt wenn man das bauen und wirklich nachsehen kann, was da 
so passiert. :-)

Damit wäre das hier mein Vorschlag:
1
    #if defined (STM32F407xx)
2
    
3
    #include "stm32f4xx.h"
4
5
    #define EVE_CS_PORT GPIOD
6
    #define EVE_CS GPIO_PIN_12
7
    #define EVE_PDN_PORT GPIOD
8
    #define EVE_PDN GPIO_PIN_13
9
    #define EVE_SPI SPI1
10
    
11
    #define DELAY_MS(ms) HAL_Delay(ms)
12
      
13
    static inline void EVE_pdn_clear(void)
14
    {
15
      HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_SET);
16
    }
17
18
    static inline void EVE_pdn_set(void)
19
    {
20
      HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_RESET);
21
    }
22
23
    static inline void EVE_cs_clear(void)
24
    {
25
//      EVE_CS_PORT->BSRR = EVE_CS;
26
      HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_SET);
27
    }
28
29
    static inline void EVE_cs_set(void)
30
    {
31
//      EVE_CS_PORT->BSRR = (uint32) EVE_CS << 16;
32
      HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_RESET);
33
    }
34
35
    static inline void spi_transmit(uint8_t byte)
36
    {
37
         LL_SPI_TransmitData8(EVE_SPI, byte);
38
         while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
39
         LL_SPI_ReceiveData8(EVE_SPI); /* dummy read-access to clear SPI_SR_RXNE */
40
    }
41
42
    static inline void spi_transmit_async(uint8_t byte)
43
    {
44
      #if EVE_DMA
45
        EVE_dma_buffer[EVE_dma_buffer_index++] = data;
46
      #else
47
           LL_SPI_TransmitData8(EVE_SPI, byte);
48
           while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
49
           LL_SPI_ReceiveData8(EVE_SPI); /* dummy read-access to clear SPI_SR_RXNE */
50
      #endif
51
    }
52
53
    static inline uint8_t spi_receive(uint8_t byte)
54
    {
55
         LL_SPI_TransmitData8(EVE_SPI, byte);
56
         while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
57
         return LL_SPI_ReceiveData8(EVE_SPI);
58
    }
59
60
    static inline uint8_t fetch_flash_byte(const uint8_t *data)
61
    {
62
      return *data;
63
    }
64
65
    #endif  /* STM32F407xx */

Das HAL_GPIO_WritePin() braucht zwar ein paar Takte mehr, das fällt aber 
nicht wirklich auf und im Gegenzug ist das auch gar nicht mehr 
STM32F407, sondern STM32F4xx.
Für EVE_pdn_clear() / EVE_pdn_set() ist der Overhead irrelevant.
Für EVE_cs_set() / EVE_cs_clear() ist das auch nicht relevant, weil man 
für eine große Display-Liste sowieso besser den Burst-Modus benutzt, ob 
nun mit DMA oder nicht, damit hat man für den ganzen Datenblock nur noch 
ein set/clear Paar und vor allem nur noch einmal am Anfang des Blocks 
die Ziel-Adresse.

Und bei einzelnen Komandos merkt man die paar Takte Overhead sowieso 
nicht.

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Okay, ich habe ein neues PlatformIO Projekt erstellt.
Als Board habe ich einfach eine Drucker-Platine mit STM32F407 
ausgewählt.

--------------------------------------------------------------
Das ist nicht funktional und dient nur als Test ob das baut!
This does not work, the purpose is to see if it compiles!
--------------------------------------------------------------

Da wird nichts initialisiert, weder der Controller, noch die IOs oder 
der SPI.
Und die while(1) dreht einfach frei, die TFT_display() darf nur so alle 
20ms aufgerufen werden.

Nothing gets initialised, not the Core, or the IOs or the SPI.
And TFT_display() has to be called once every 20ms or more.


Ich musste die EVE_target.h jetzt doch noch ein wenig erweitern.
Ich dachte ja eigentlich, dass die HAL gleich mit includiert wird,
das war aber nichts.
1
#if defined (STM32F4)
2
    
3
#include "stm32f4xx.h"
4
#include "stm32f4xx_hal.h"
5
#include "stm32f4xx_ll_spi.h"
6
...

Edit, ich habe gerade noch aus dem STM32F407xx ein STM32F4 gemacht, das 
müsste soweit für die ganze Familie gelten.

Edit2: jetzt wüsste ich gerne noch, wie man Anhänge löscht :-)

: Bearbeitet durch User
von M. B. (mokkka)


Lesenswert?

Rudolph R. schrieb:
> Da die EVE_commands.c die EVE_target.h includiert wird damit implizit
> oder explizit auch die stdint.h mit includiert.
> Für AVR, ATSAM, RISC-V und auch STM32 passiert das automatisch über die
> System-Includes.
> #include "stm32f4xx.h" -> #include "stm32f407xx.h" -> #include
> <stdint.h>

Das Problem entsteht auch nicht in der EVE_commands.c sondern 
EVE_commands.h. die EVE_commands.c ist soweit glücklich und hat alles

Rudolph R. schrieb:
> Delays an welcher Stelle?
> Wie schnell hast Du den SPI laufen? Zumindest für das Init sollte das
> unter 11MHz sein, dann unter 30MHz wobei die Hardware das auch mit
> machen muss.

Am Anfang um die 6 MHz danach würde ich gerne auf 21 MHz es funktioniert 
aber nur bis 10,5 MHz

Gegenvorschlag =). Das Problem liegt tatsächlich an dem RXNE Flag. Man 
muss mit dem Read allerdings warten bis das Flag geworfen wird. Der Chip 
rennt an dieser Stelle schneller als der SPI_Bus dementsprechend muss 
auf das
Flag gewartet werden.

1
    #if defined (STM32F407xx)
2
    
3
    #include "stm32f4xx.h"
4
5
    #define EVE_CS_PORT GPIOD
6
    #define EVE_CS GPIO_PIN_12
7
    #define EVE_PDN_PORT GPIOD
8
    #define EVE_PDN GPIO_PIN_13
9
    #define EVE_SPI SPI1
10
    
11
    #define DELAY_MS(ms) HAL_Delay(ms)
12
      
13
    static inline void EVE_pdn_clear(void)
14
    {
15
      HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_SET);
16
    }
17
18
    static inline void EVE_pdn_set(void)
19
    {
20
      HAL_GPIO_WritePin(EVE_PDN_PORT, EVE_PDN, GPIO_PIN_RESET);
21
    }
22
23
    static inline void EVE_cs_clear(void)
24
    {
25
//      EVE_CS_PORT->BSRR = EVE_CS;
26
      HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_SET);
27
    }
28
29
    static inline void EVE_cs_set(void)
30
    {
31
//      EVE_CS_PORT->BSRR = (uint32) EVE_CS << 16;
32
      HAL_GPIO_WritePin(EVE_CS_PORT, EVE_CS, GPIO_PIN_RESET);
33
    }
34
35
    static inline void spi_transmit(uint8_t byte)
36
    {
37
         LL_SPI_TransmitData8(EVE_SPI, byte);
38
         while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
39
         while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
40
         LL_SPI_ReceiveData8(EVE_SPI); /* dummy read-access to clear SPI_SR_RXNE */
41
    }
42
43
    static inline void spi_transmit_async(uint8_t byte)
44
    {
45
      #if EVE_DMA
46
        EVE_dma_buffer[EVE_dma_buffer_index++] = data;
47
      #else
48
           LL_SPI_TransmitData8(EVE_SPI, byte);
49
           while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
50
           while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
51
           LL_SPI_ReceiveData8(EVE_SPI); /* dummy read-access to clear SPI_SR_RXNE */
52
      #endif
53
    }
54
55
    static inline uint8_t spi_receive(uint8_t byte)
56
    {
57
         LL_SPI_TransmitData8(EVE_SPI, byte);
58
         while(!LL_SPI_IsActiveFlag_TXE(EVE_SPI));
59
         while(!LL_SPI_IsActiveFlag_RXNE(EVE_SPI));
60
         return LL_SPI_ReceiveData8(EVE_SPI);
61
    }
62
63
    static inline uint8_t fetch_flash_byte(const uint8_t *data)
64
    {
65
      return *data;
66
    }
67
68
    #endif  /* STM32F407xx */

Bis auf die Geschwindigkeit und die inttypes in der commands.h scheint 
es zu laufen.

von Rudolph R. (rudolph)


Lesenswert?

M. B. schrieb:
> Das Problem entsteht auch nicht in der EVE_commands.c sondern
> EVE_commands.h. die EVE_commands.c ist soweit glücklich und hat alles

Ah okay, dagegen habe ich in EVE_target.c und tft.c erst das
EVE_target.h und dann EVE_commands.h.

Intuitiver ist aber vielleicht ein #include "EVE_target.h"
direkt in die EVE_commands.h zu packen.

M. B. schrieb:
> Gegenvorschlag =). Das Problem liegt tatsächlich an dem RXNE Flag. Man
> muss mit dem Read allerdings warten bis das Flag geworfen wird. Der Chip
> rennt an dieser Stelle schneller als der SPI_Bus dementsprechend muss
> auf das Flag gewartet werden.

Ich habs eingebaut, danke.
Die SPI Unit von zumindest dem STM32F4 ist schon ein wenig seltsam.
Alternativ bliebe noch das Busy-Flag abzufragen.
Das Kapitel 28.3.7 vom Referenz-Manual ist da aber etwas komisch.
Es gibt weder ein BDM noch ein BDOE Bit.

Das dürften BIDIMODE und BIDOE sein so vom Kontext her.
Mit MSTR = 1, BIDIMODE = 0 und BIDOE = 1 sollte das passen.

Aber dann kommt der nächste Satz:
"It is cleared:
• when a transfer is finished (except in master mode if the 
communication is continuous)"

Was soll das denn bitte heissen?
Unter welchen Umständen ist der SPI Transfer kontinuierlich?
Wenn man DMA benutzt?
Falls das so ist, warum sollte man mit den Status Bits rumspielen wenn 
gerade ein DMA Transfer läuft?


Edit:
>Am Anfang um die 6 MHz danach würde ich gerne auf 21 MHz es funktioniert
>aber nur bis 10,5 MHz

Das ist vor allem auch eine Frage der Hardware.
Mit meinen aktuellen ATSAMC21 Platinen kann ich 12MHz ohne 
Einschränkungen verwenden, also nach dem Init.
Wenn ich auf 24MHz hoch stelle funktioniert allerdings der Touch nicht 
mehr, also irgendwie läuft das mit MISO nicht rund.

: Bearbeitet durch User
von Ioan Mihai Cozac (Gast)


Lesenswert?

Hallo Rudolf,

Erstmal Danke für deine erstklassiger Bibliothek, sie hat mir viel Zeit 
erspart.
Ich arbeite gerade bei einem Projekt in medizinische Bereich, dabei 
werden verschiedene Figuren und Texte teilweise animiert dargestellt, 
soweit funktioniert alles glücklicherweise wie gedacht.
Verwendet wird bei meinem Projekt ein 7" FT813 Display von Riverdi, und 
jetzt kommt mein problem: da die Pixels des displays nicht perfekt 
quadratisch sind die runde Formen wie Punkte und Kreisel werden leicht 
oval dargestellt.
Soweit habe keine Möglichkeit gefunden dies in Software zu kompensieren. 
Grundsätzlich müstte glaube ich ein Faktor von abs(sin(0,93 * PI) von 
Radius des Zirkels extrahieren sodass in verschiedene Richtungen dies 
unterschiedliche Länge hat. Also wie EVE_cmd_dl(POINT_SIZE (x - faktor) 
* 16).
Leider funktioniert das nicht wie erwartet, mir bleibt es immerhin oval.
Bei FTDI gibt auch keine weitere details über Primitives.
Sorry für meine Sprache, bin keiner nativen Deutschsprecher.

PS mit einem Display von Glyn funktioniert alles super, nur sind die 
vielmehr teurerer...

von Rudolph (Gast)


Lesenswert?

Puh, ich muss zugeben, dass mir das bisher nicht mal aufgefallen ist, 
die Abweichung ist ja auch eher dezent.
Und ich benutze eher nur kleine Kreise.


Medizin ist ja mal interessant.
Wird das tatsächlich ein Produkt?
Welcher MikroController kommt da zum Einsatz?


Meine erste Idee war jetzt mal bei Matrix Orbital zu schauen, aber dem 
Datenblatt nach hat deren 7" Panel ein Pixel-Pitch von 0.1923*0.1784 und 
ist damit minimal "schlechter" als das Panel von Riverdi.

Wobei jetzt noch interessant gewesen wäre, welches Display das von 
Riverdi genau ist, ich habe mir jetzt nur das Datenblatt von den 
RVT70UQFNWC0x angesehen.

Die dritte Adresse für FT813 Displays wäre Newhaven, sowas wie das hier: 
https://www.newhavendisplay.com/nhd70800480ftctxlctp-p-9579.html

Da finde ich aber gerade gar keine Angabe im Datenblatt zum Pixel-Pitch, 
dazu müsstest Du denen mal eine Support-Anfrage einstellen.

Die haben auch mechanisch eine etwas andere Schnittstelle.


Direkt manipulieren kann man die "Primitives" nicht, die landen im 
Gegensatz zu den "Widgets" direkt so in der Display-Liste.
Und sowas wie CMD_SCALE wirkt sich nur auf Bilder aus, nicht etwa auf 
POINTS.

Eine Alternative zu einem anderen Display wäre noch auf POINTS ganz zu 
verzichten und das mit Bitmaps zu machen die vorab so verzerrt werden, 
dass sich das mit der Anzeige dann wieder ausgleicht.

Wenn der FT813 damit in der Anwendung nicht mehr funktioniert, weil 
einfach der Grafik-Speicher jetzt schon voll ist, schau Dir mal die 
BT815 basierten Displays von Riverdi und Matrix Orbital an.
Die haben ein SPI-FLASH mit auf der Platine das von dem BT815 
angesprochen wird, da kann man unter anderem Bilder rein packen die 
direkt angezeigt werden können.
Beschrieben wird der SPI-FLASH am bequemsten mit einem USB-SPI Interface 
was es ebenfalls von Riverdi oder Matrix Orbital gibt.

von TFTLCDCyg (Gast)


Angehängte Dateien:

Lesenswert?

The 7 "HD screen also has that uniqueness relative to" careless pixels "

Rudolph has considered using a microSD reader in your library, it is 
much more convenient to upload images on the GRAM of the FT81X screen, 
without running out of memory or complicating the code.

By the way, have you managed to upload videos in avi format with audio 
on the FT81x processor?

von Rudolph R. (rudolph)


Lesenswert?

TFTLCDCyg schrieb:
> Rudolph has considered using a microSD reader in your library, it is
> much more convenient to upload images on the GRAM of the FT81X screen,
> without running out of memory or complicating the code.

I have considered it and just switched to a bigger controller. :-)
More seriously this is just out of scope for my code.
Sure, combining mass storage with EVE could be beneficial but apart from 
mayb e a helper function to transfer a memory buffer to EVE that is not 
my job.

And this function already exists for every other architecture than AVR 
in form of the code that reads from flash.
On ARM this can read from anywhere.

> By the way, have you managed to upload videos in avi format with audio
> on the FT81x processor?

Others have, but I have not even tried this so far.
This is just not what I use the FT81x/BT81x for.

von Ioan Mihai Cozac (Gast)


Angehängte Dateien:

Lesenswert?

The project is a time controller associated with low power therapy laser 
devices. It counts the various intervals needed for bacteria 
desinfection in mouth and teeths using laser beams. It displays among 
other information both progress circular sectors and various sounds 
every 10, 30 or 60 seconds.
I designed this using an ESP32 as microcontroller, there will be a 
wireless link between the laser device and the time controller but this 
is not important here. The internal flash is big enough to store all the 
necesarry pieces of code and images.
Yesterday came another display from Riverdi this one is the BT815 
version, although the same LCD, so the ovalizing problem remains. We 
bought it because of the "umlaut" problem of the FT8xx series, we need 
the infos to be displayed in several languages.
So there is no easy way to fix the picture distortion, i think we will 
choose the expensive better displays from Glyn.

von Rudolph (Gast)


Lesenswert?

While it is not really obvious for me when I look at the picture, 
measuring height and width shows a clear deviation, yes.

When you already use BT815 for extended font support, why not use 
pictures for the circles?
After all, these have 64MBit of FLASH installed and a few additional 
bitmaps should be easily possible, even more so when using ASTC 
compressed images directly from the external FLASH.

And does Glyn even offer a 7" with BT815?

von Ioan Mihai Cozac (Gast)


Lesenswert?

I should have 60 or 90 different pictures for every display situation... 
and that for more than 10 different circular elements. I should compute, 
draw and store hundreds of bitmaps...
Such a circular sector widget has the following code:
[c]
FT8_cmd_dl(DL_BEGIN | FT8_LINES);
    FT8_cmd_dl(DL_COLOR_RGB | RED);
    FT8_cmd_dl(LINE_WIDTH(1 * 16));
    int r1 = 77, r2 = 128;
    for (int t1 = 0; t1 < 6; t1++)
    { // DRAWING 6 SEGMENTS 60 DEGREES AROUND MAIN CIRCLES
      float t = (t1 / 3.00) * PI;
      FT8_cmd_dl(VERTEX2F(x * 16 + (int)(r1 * sin(t)) * 16, y * 16 - 
(int)(r1 * cos(t)) * 16));
      FT8_cmd_dl(VERTEX2F(x * 16 + (int)(r2 * sin(t)) * 16, y * 16 - 
(int)(r2 * cos(t)) * 16));
    }
    FT8_cmd_dl(LINE_WIDTH(7 * 16));
    //FT8_cmd_dl(DL_COLOR_RGB | RED);
    byte segments = (sec_2 / 10) * 10 + 10; // HALF WIDTH POSITIVE 
OFFSET
    for (int t1 = 0; t1 < segments; t1++)
    { // DRAWING 30 SEGMENTS BARGRAPH AROUND TIME COUNTER
      float t = (t1 / 30.00) * PI + (0.5 / 30.00) * PI;
      if (min_2 < min2_max || sec_2 < sec2_max) //PROPER DISPLAY OF THE 
RED SEGMENTS
      {
        FT8_cmd_dl(VERTEX2F(x * 16 + (int)(r1 * sin(t)) * 16 + 
(int)(abs(32 * cos(t))), y * 16 - (int)(r1 * cos(t)) * 16));
        FT8_cmd_dl(VERTEX2F(x * 16 + (int)(r2 * sin(t)) * 16, y * 16 - 
(int)(r2 * cos(t)) * 16));
      }
    }
[c/]

Glyn has sent us a custom board for test, but our old display is only 6 
bit so the picture is not properly displayed. They said they could 
produce them for us if enough pieces will be ordered.

von Rudolph (Gast)


Lesenswert?

Ioan Mihai Cozac schrieb:
> I should have 60 or 90 different pictures for every display situation...
> and that for more than 10 different circular elements. I should compute,
> draw and store hundreds of bitmaps...

I see, that would be indeed a lot of additional work.

Ioan Mihai Cozac schrieb:
> FT8_cmd_dl(DL_BEGIN | FT8_LINES);

Oh, so are using an older 3.x version.
I changed the FT8_ prefixes to EVE_ prefixes a long time ago.
While most of the changes have been for BT81x, there also have been a 
number of additions and fixes for the older generations.

von Ioan Mihai C. (mihaicozac)


Lesenswert?

Yes indeed...
I will try the new version on the new BT815 display, i think all the 
settings are the same only the EVE_HAS_CRYSTAL should be set to 1.

von Bernd I. (Firma: Ickert-Elektronik) (bernd2201)


Lesenswert?

Hallo und viel Erfolg im neuen Jahr!
Hat schon mal jemand ein Display der Firma ACTRON mit C-Touch am FT813 
betrieben? Lt. Datenblatt des Display hat er ein C-Touch-Controller 
HY4635 mit der I2C-Adresse Hx38. Mit dem Ossci kontrolliere ich Data und 
Takt der I2C-Schnittstelle. Und der FT813 spricht den HY4635 auch mit 
dieser Adresse an, es kommt das ACK und dann nur noch ein nicht 
vollständiges Byte - Schluss! Das Merkwürdigste ist dabei, dass die 
Taktleitung dauerhaft auf Low liegt (müsste aber in Ruhe auf High 
liegen). Gibt es noch irgend ein Register des FT813 (C-Touch-Register), 
was vielleicht in diesem Fall noch entsprechend gesetzt werden muss?
Benutze ich das DEMO-Board mit FT813 und mit 5" Display (Bridgetek), so 
funktioniert mit meiner selben Software natürlich alles. Ich setze 
lediglich am Beginn einmal den REG_CTOUCH_MODE und REG_CTOUCH_EXTEND und 
kann dann z.B. den Register REG_CTOUCH_TOUCH_XY auslesen und erhalte die 
Koordinaten. Auf der I2C-Schnittstelle des Demo-Board sehe ich die 
ordnungsgemäße Kommunikation mit dem Ossci. Hier ist die Takt-Leitung 
auf High, wenn keine Kommunikation statt findet.
Hat jemand einen Tipp?????

von Rudolph R. (rudolph)


Lesenswert?

Dazu ist gerade eine Diskussion im BRT Community Forum durch: 
http://www.brtcommunity.com/index.php?topic=62.0

Und so wie es aussieht verkauft Actron Displays von Powertip,
das passt dann also praktisch genau auf den Thread.

Um welches Modell geht es denn konkret?

Die Kurzversion ist das  man den Touch-Controller im FT813 minimal 
patchen muss um den I2C Takt niedriger einzustellen.

Edit: was zum Geier meint Actron mit I³?
Das sind doch gar keine intelligenten Displays.

Edit2: ich würde das ja auch gerne ausprobieren, aber dazu müsste ich 
dann erstmal eine Platine designen an die man so ein Display 
anschliessen kann -> dann doch lieber nicht.

: Bearbeitet durch User
von Bernd I. (Firma: Ickert-Elektronik) (bernd2201)


Angehängte Dateien:

Lesenswert?

Hallo Rudi,
guter Tipp mit "minimaler Patch". I2C ist ja allgemein bekannt als 
langsame Schnittstelle, max. 160khz (ca.). Das messe ich mal nach, was 
der FT813 da macht (Geschwindigkeit)… Und wie könnte ich die 
Geschwindigkeit dieser Schnittstelle am FT813 ändern ?????????????
Es geht konkret um das SH800480TO13-IHC09, aber das spielt keine Rolle, 
glaube ich, da ich von ACTRON leichtsinniger Weise mal vor ein paar 
Monaten schon 40 Stück verschiedener Baugrößen und Art (10x 4,3"; 10x7" 
und je 10 mit Glas-Überstand und Glas-Abschließend) geordert hatte und 
das Problem sowohl mit dem 4,3-, als auch mit dem 7-Zöller habe. Das 
geniale an den ACTRON mit ACT I3 Anschlüssen ist, dass die damit genau 
"mein" Problem gelöst haben: Es gibt so viele Displays und jedes hat 
einen anderen Anschluss (das 40-50-polige Folienkabel). "Natürlich" sind 
das keine intelligenten Displays, einfach nur Displays. Und dafür habe 
ich mir nun Display-Treiber-PLatinen mit dem FT813 gebaut und kann dank 
der ACT I3 verschiedene Display für verschiedene Anwendungen mit dem 
einen Treiber realisieren - wenn ich denn das mit dem C-Touch noch 
hinbekomme!!! Schlimmstenfalls spreche ich diese Schnittstelle am FT813 
vorbei direkt mit meinem Prozessor an … Ich weiß, wie ich dich kenne 
krämpeln sich jetzt bei dir alle Fußnägel hoch - von wegen 
"Vergewaltigung" des FT8xx . Das ist wie mit "an dem Co-Prozessor" 
vorbei selbst Buttons generieren.. Hatte dazu ja schon meinen "Rüffel" 
von Dir bekommen!
Danke für den Link zum Thread. Schaue mich da jetzt mal um!

von Bernd I. (Firma: Ickert-Elektronik) (bernd2201)


Lesenswert?

OK - Exakter geht es ja tatsächlich nicht! Habe ich also nicht allein 
das Problem. Wie es aus der Diskussion hervorgeht, ist es tatsächlich 
ein Geschwindigkeitsproblem und Hinweise zur Veränderung der 
Taktgeschwindigkeit des FT813 sind dort auch zu finden. Na dann probiere 
ich mal. Und in diesem Fall scheint mir die Bedienung dieser 
Schnittstelle am FT vorbei direkt durch meinen Prozessor immer weniger 
abwegig!!!

von Rudolph R. (rudolph)


Lesenswert?

Bernd I. schrieb:
> I2C ist ja allgemein bekannt als
> langsame Schnittstelle, max. 160khz (ca.). Das messe ich mal nach, was
> der FT813 da macht (Geschwindigkeit)…

I2C hat normalerweise 100kHz oder 400kHz und es gibt auch noch HighSpeed 
Versionen mit 1MHz oder so.
Die FT81x/BT81x machen 400kHz und der HY4635 ist mit 100kHz glücklicher.


Bernd I. schrieb:
> Und wie könnte ich die
> Geschwindigkeit dieser Schnittstelle am FT813 ändern ?????????????

Den Wert 40 an Adresse 0x30b1ac schreiben.
Das gibt 58kHz und mit 20 bekommt man wohl so 98kHz.

Die Bilder sieht man in dem Forum meine ich nur wenn man da angemeldet 
ist.
Die haben ein "code.png" angehängt.

Und da steht drin:
1
/* Hycon fix */
2
delay(50);
3
Gpu_Hal_Wr8(host, REG_CPURESET, 2);
4
Gpu_Hal_Wr8(host, 0x301b1ac, 40);
5
Gpu_Hal_Wr8(host, REG_CPURESET, 0);

Also EVE_memWrite8().

Und danach besser noch so eine Schleife wie in EVE_init():
1
  timeout = 0;
2
  while (0x00 != (EVE_memRead8(REG_CPURESET) & 0x03)) /* check if EVE is in working status */
3
  {
4
    DELAY_MS(1);
5
    timeout++;
6
    if(timeout > 50)
7
    {
8
      return 0;
9
    }
10
  }

Der Touch-Controller braucht nämlich ein wenig bis er wieder aus dem 
Reset da ist.

Oder eben einfach nur ein delay(50) oder so.


Bernd I. schrieb:
> Das
> geniale an den ACTRON mit ACT I3 Anschlüssen ist, dass die damit genau
> "mein" Problem gelöst haben: Es gibt so viele Displays und jedes hat
> einen anderen Anschluss (das 40-50-polige Folienkabel).

Also im Grunde genommen das was Glyn auch mit dem "Familie Konzept" 
macht.
Und solche Faxen mit den Display-Anschlüssen sind genau der Grund warum 
ich lieber fertige Module verwende. :-)

Bernd I. schrieb:
> Und dafür habe
> ich mir nun Display-Treiber-PLatinen mit dem FT813 gebaut

Hat auch was, jetzt noch auf BT815 aufrüsten, einen Controller dazu und 
einen 3,3V Regler. :-)

Nein im Ernst, niedliches Platinchen.
Die Displays haben einen Regler für die Beleuchtung integriert?
12V ist da schon etwas ungewöhnlich.

Bernd I. schrieb:
> Schlimmstenfalls spreche ich diese Schnittstelle am FT813
> vorbei direkt mit meinem Prozessor an … Ich weiß, wie ich dich kenne
> krämpeln sich jetzt bei dir alle Fußnägel hoch - von wegen
> "Vergewaltigung" des FT8xx .

Keine Ahnung was Du meinst. :-)
Es gibt genau für sowas den sogenannten "Host" Mode bei dem der 
Controller im Ziel-System die I2C Kommunikation mit dem Touch-Controller 
abwickelt und die Daten an den FT81x schickt damit dieser die auswertet.
Das ist sicherlich lästig und I2C gefällt mir so oder so nicht, aber 
bevor man eben gar keinen Touch hat, weil EVE nicht mit dem 
Touch-Controller spielen will...

von Bernd I. (Firma: Ickert-Elektronik) (bernd2201)


Lesenswert?

Rudi schrieb:
Die Bilder sieht man in dem Forum meine ich nur wenn man da angemeldet
ist.
Die haben ein "code.png" angehängt.

Und da steht drin:
/* Hycon fix */
delay(50);
Gpu_Hal_Wr8(host, REG_CPURESET, 2);
Gpu_Hal_Wr8(host, 0x301b1ac, 40);     ICH HOFFE, DAS IST EIN 
SCHREIBFEHLER !
Gpu_Hal_Wr8(host, REG_CPURESET, 0);

Hallo Rudi,
ich traue mich nicht so recht, in den Bereich 30b1ac einen Wert zu 
schreiben (die 40). Dieser Bereich ist im Datenblatt nirgendwo 
benannt/beschrieben!
Der letzte Bereich endet bei 308FFF (der Command Buffer). Und ich hoffe, 
das da oben ist ein Schreibfehler - eine Eins zu viel hinter der 30. 
Denn der Herr "BRT Community" schreibt ja auch vom 30b1ac oder den 
RAM_JBOOT + 1ac.
Über den RAM_JBOOT finde ich nichts !!! Soll ich also ??? :):) Und an 
anderer Stelle schreibts Du selbst auch 30b1ac
Denn wenn man mal eben an eine falsche Stelle etwas schreibt, kann der 
FTI danach auch hinüber sein!

Das mit den 12V für die Hintergrundbeleuchtung ist tatsächlich etwas 
ungewöhnlich, bedeutet aber eben nur eine Ader zu meinem "Platinchen" 
mehr. Der Regler ist auf dem Display, der kommt aber eben nicht mit 3,3V 
aus, sondern braucht mind. 5V (max. 17V).

OK ich traue mich jetzt!

von Bernd I. (Firma: Ickert-Elektronik) (bernd2201)


Lesenswert?

Ich habe mich getraut !!!
Nachdem sich die Rauchwolke verzogen hatte …

Nein - alles Super. I2C arbeitet jetzt auf 57kHz (gemessen) und der 
Touch funktioniert! Auf alles andere hat diese Taktveränderung doch wohl 
keinen Einfluss ???

von Bernd I. (Firma: Ickert-Elektronik) (bernd2201)


Lesenswert?

Da meine "Platinchen" ja nun zu 100% so funktionieren, wie ich es mir 
gedacht hatte, kann ich ja mal 100 Stück davon fertigen lassen (wir 
machen bei uns im Haus, außer ein paar Muster keine SMD-Bestückung, nur 
THT). Möchtest Du eine davon? Würde ich Dir schenken, als kleines 
Dankeschön für die Hilfe!!!
Aber die sind eben nur für die ACTRON-Display's nützlich!

Schönen Sonntag noch.

von Rudolph R. (rudolph)


Lesenswert?

Bernd I. schrieb:
> Über den RAM_JBOOT finde ich nichts !!! Soll ich also ??? :):) Und an
> anderer Stelle schreibts Du selbst auch 30b1ac

Ja, Tippfehler. :-)
RAM_JBOOT gibt es auch nirgendwo in den Unterlagen, das stammt sicher 
aus internen Unterlagen von FTDI/Bridgetek.

Das ist der Bereich in dem der Code für den Touch-Controller liegt.
da kann man auch nichts kaputt machen, von der Architektur sehen die EVE 
nämlich so aus, dass die ein ROM haben (oder vielleicht auch ein FLASH), 
das beim Start in RAM kopiert wird, ein Shadow-RAM.
So funktionieren auch die FT9xx von FTDI.
Man kann den Speicher zwar nicht auslesen, aber beschreiben geht.

In AN_336 gibt es Binär-Blobs die an diese Stelle kopiert werden.
Das sieht man da nicht direkt, da der Blob in den Kommando Co-Processor 
geschrieben und ausgeführt wird.
Wenn man das aber zerlegt, kommt man schnell dahinter das da im 
wesentlichen ein CMD_INFLATE die Daten an 0x3b1ac entpackt.

Spannende Sache, die EVE sind also patchbar, viel weiter als das bin ich 
aber noch nicht gekommen, da sich FTDI/BRT da sehr bedeckt hält.
Die haben intern sicherlich ein SDK dafür.
Was die in den Thread gepackt haben hat mich jetzt ein wenig überrascht.

Bernd I. schrieb:
> Möchtest Du eine davon? Würde ich Dir schenken, als kleines
> Dankeschön für die Hilfe!!!
> Aber die sind eben nur für die ACTRON-Display's nützlich!

Ich würde eine nehmen, klar, ab in die Sammlung. :-)
Aber erstmal muss ich schauen ob ich ein Display dafür bekomme.
Actron sind aber nicht die einzigen die Displays von Powertip 
vertreiben.
Dann 8 Fädeldrähte und es sollte laufen. :-)

von Rudolph R. (rudolph)


Lesenswert?

Interessant, Powertip hat FT813 Displays im Sortiment von denen ich noch 
nie gehört habe.

PH800480T024-IFC03 5"
PH800480T013-IFC05 7"

Leider kann ich dazu nichts finden, keine Datenblätter, kein 
Distributor.

von Rudolph R. (rudolph)


Lesenswert?

Rudolph R. schrieb:
> Bernd I. schrieb:
>> Möchtest Du eine davon? Würde ich Dir schenken, als kleines
>> Dankeschön für die Hilfe!!!
>> Aber die sind eben nur für die ACTRON-Display's nützlich!
>
> Ich würde eine nehmen, klar, ab in die Sammlung. :-)

Okay, ich habe intensiv gesucht und ich würde dann eher doch keines 
nehmen, aber vielen Dank für das Angebot!

Dazu passen praktisch nur eine Handvoll Displays:

PH320240T023-IHC04 PH320240T023-IHC06
PH480272T009-IHC05 PH480272T009-IHC07
PH800480T024-IHC07 PH800480T024-IHC11
PH800480T013-IHC09 PH800480T013-IHC12

Und die bekomme ich zum einen allesamt nicht einfach so bestellt.
Dann fallen die ersten 4 mit 3,5" und 4,3" auch praktisch gleich raus.

Wenn man tatsächlich Produkte verkauft sieht die Sache sicher anders 
aus, dann kann man da über die Mengen ganz anders heran gehen.

Da die Ganze Geschichte für mich aber eher ein Hobby ist, wenn auch mit 
dem Benefit gelegentlich dienstlich Arbeit zu generieren, kaufe ich 
Displays nur in niedrigen einstelligen Stückzahlen.
Ich habe gerade ein 5" EVE2-50G auf dem Tisch das als Einzelstück an 
einen Kunden geht.
Und daneben liegt ein 4,3" EVE3-43G für das ich eine Demo-Software 
vorbereite um Kollegen davon zu überzeugen die Neu-Auflage eines 
Haus-internen Tools mit Display zu machen.
Davon brauche ich dann vielleicht mal >10 Stück.
Als nächstes werde ich dann wohl wieder ein 7" als Einzelstück in einen 
Testplatz stecken dürfen.
Okay, ich habe praktisch den ganzen Spass ohne Probleme wie 
Produktkosten wirklich berücksichtigen zu müssen. :-)

Also für mich lohnt sich das einfach nicht einzelne Displays mit eigenen 
FT81x/BT81x Platinen zu verwenden

von Ioan Mihai C. (mihaicozac)


Lesenswert?

Found a pretty simple workaround for the ovalization, i draw 2 points 
for every point needed, with the center vertically misaligned, about 6% 
of the radius of points. Mathematically is not quite a perfect circle 
but optically looks much better as before.
But i have some trouble with the newest version of your EVE, there is an 
error that appears regarding the SPI library. It apperas regardless if i 
use the FT813 or the BT815 display.
IDE is VS Code for Platform.io, microcontroller is ESP32 and the error 
is like this:
1
In file included from src\EVE_target.h:849:0,
2
                 from src\EVE_commands.c:192:
3
C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\libraries\SPI\src/SPI.h:28:1: error: unknown type name 'class'
4
 class SPISettings
5
 ^
6
C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\libraries\SPI\src/SPI.h:29:1: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
7
 {
8
 ^
9
In file included from src\EVE_target.h:849:0,
10
                 from src\EVE_commands.c:192:
11
C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\libraries\SPI\src/SPI.h:38:1: error: unknown type name 'class'
12
 class SPIClass
13
 ^
14
C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\libraries\SPI\src/SPI.h:39:1: error: expected '=', ',', ';', 'asm' or '__attribute__' before '{' token
15
 {
16
 ^
17
C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\libraries\SPI\src/SPI.h:86:8: error: unknown type name 'SPIClass'
18
 extern SPIClass SPI;
19
        ^
20
In file included from C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\cores\esp32/Arduino.h:35:0,
21
                 from src\EVE_target.h:850,
22
                 from src\EVE_commands.c:192:
23
C:\Users\Mihai\.platformio\packages\framework-arduinoespressif32\cores\esp32/esp32-hal.h:48:0: warning: "NOP" redefined
24
 #define NOP() asm volatile ("nop")
25
 ^
26
In file included from src\EVE_commands.c:191:0:
27
src\EVE.h:755:0: note: this is the location of the previous definition
28
 #define NOP() ((45UL<<24))
29
 ^
30
In file included from src\EVE_commands.c:192:0:
31
src\EVE_target.h: In function 'EVE_cs_set':
32
src\EVE_target.h:882:6: error: request for member 'setDataMode' in something not a structure or union
33
   SPI.setDataMode(SPI_MODE0);
34
      ^
35
src\EVE_target.h: In function 'spi_transmit_async':
36
src\EVE_target.h:894:7: error: request for member 'write' in something not a structure or union
37
    SPI.write(data);
38
       ^
39
src\EVE_target.h: In function 'spi_transmit':
40
src\EVE_target.h:899:7: error: request for member 'write' in something not a structure or union
41
    SPI.write(data);
42
       ^
43
src\EVE_target.h: In function 'spi_receive':
44
src\EVE_target.h:915:13: error: request for member 'transfer' in something not a structure or union
45
   return SPI.transfer(data);
46
             ^
47
src\EVE_target.h:916:2: warning: control reaches end of non-void function [-Wreturn-type]
48
  }
49
  ^

Using the older FT8... library the program compiles and runs OK.

: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

Ioan Mihai C. schrieb:
> Found a pretty simple workaround for the ovalization, i draw 2 points
> for every point needed, with the center vertically misaligned, about 6%
> of the radius of points. Mathematically is not quite a perfect circle
> but optically looks much better as before.

Interesting, thank you for the suggestion.

Ioan Mihai C. schrieb:
> But i have some trouble with the newest version of your EVE, there is an
> error that appears regarding the SPI library.

This is a "feature" of Arduino that for "reasons" the classes are not 
supposed to work with plain .c files.
It should work just fine if you rename "EVE_commands.c" to 
"EVE_commands.cpp".

There might be a solution to fix that without renaming the file but I 
have not found one yet and I am normally not reminded about this since I 
am normally not using the Arduino framework.

Plus that renaming the file works kind of tells me that the issue is not 
really on my side...

von Karol B. (karol_b135)


Lesenswert?

Hi Rudolph! A lot of thanks for your job. I still have very old lib, its 
working with FT800 and FT810 well. I have RVT70UQFNWC00 from Riverdi and 
a lot of problems with it. Pleas visit url link, there are schematic, 
PCB, some C listing and movie. Could you give me an advice what I do 
wrong? I mage another project with the same tft panel and its workinkg 
well. Im getting crazy, I spent more then 2 days traing to fix it. Pleas 
help.

Beitrag "FT800 / FT810 Library"

von Karol B. (karol_b135)


Lesenswert?

Hi Rudolph! A lot of thanks for your job. I still have very old lib, its 
working with FT800 and FT810 well. I have RVT70UQFNWC00 from Riverdi and 
a lot of problems with it. Pleas visit url link, there are schematic, 
PCB, some C listing and movie. Could you give me an advice what I do 
wrong? I mage another project with the same tft panel and its workinkg 
well. Im getting crazy, I spent more then 2 days traing to fix it. Pleas 
help.
Beitrag "FT800 / FT810 Library"

https://www.elektroda.pl/rtvforum/viewtopic.php?p=18496421#18496421

von Rudolph (Gast)


Lesenswert?

Hello,

I can have a closer look when I am home again.

But please describe what the problem actually is.
I had to translate the website to Englisch and I am not sure if it got 
lost in translation but there is no description of the issue.

Also, please attach the code here as well, I would need to login to that 
other forum in order to see it.

And then, why not just switch to the latest version of my library?

von Karol B. (karol_b135)


Lesenswert?

Thanks for your answer.
There is a movie, didn't you saw it?
I have a lot of strange behavior of display. Its live on his own life, 
changing all elements on screen also pressing touch without physical 
finger touch.
1
void ft800_init(void)
2
{
3
  uint8_t chipid;
4
  uint16_t timeout = 0;
5
  
6
  FT_PDN_DDR |= FT_PDN;
7
  FT_CS_DDR |= FT_CS;
8
9
  FT_PDN_PORT &= ~FT_PDN;
10
  DELAY_MS(6);  // minimum time for power-down is 5ms
11
  FT_PDN_PORT |= FT_PDN;
12
  DELAY_MS(21);  // minimum time to allow from rising PD_N to first access is 20ms
13
14
  //ft800_cmdWrite(FT_CLKEXT);  // Set FT800 for external clock
15
  ft800_cmdWrite(FT_CLKINT);
16
  ft800_cmdWrite(FT_CLK48M);  // FT_CLK48M Set FT800 for 48MHz PLL
17
  ft800_cmdWrite(FT_ACTIVE);  // Start FT800
18
19
  chipid = ft800_memRead8(REG_ID);  // Read ID register
20
  while(chipid != 0x7C)  // if chipid is not 0x7c, continue to read it until it is, FT81x may need a moment for it's power on selftest
21
  {
22
    chipid = ft800_memRead8(REG_ID);
23
    DELAY_MS(1);
24
    timeout++;
25
    if(timeout > 400)
26
    {
27
      break;//return 0;
28
    }
29
  }
30
31
  ft800_memWrite8(REG_PCLK, 0x00);    // Set PCLK to zero - don't clock the LCD until later
32
  ft800_memWrite8(REG_PWM_DUTY, 30);    // Turn off backlight
33
34
  // Initialize Display
35
  ft800_memWrite16(REG_HSIZE,   FT_HSIZE);  // active display width
36
  ft800_memWrite16(REG_HCYCLE,  FT_HCYCLE);  // total number of clocks per line, incl front/back porch
37
  ft800_memWrite16(REG_HOFFSET, FT_HOFFSET);  // start of active line
38
  ft800_memWrite16(REG_HSYNC0,  FT_HSYNC0);  // start of horizontal sync pulse
39
  ft800_memWrite16(REG_HSYNC1,  FT_HSYNC1);  // end of horizontal sync pulse
40
  ft800_memWrite16(REG_VSIZE,   FT_VSIZE);  // active display height
41
  ft800_memWrite16(REG_VCYCLE,  FT_VCYCLE);  // total number of lines per screen, incl pre/post
42
  ft800_memWrite16(REG_VOFFSET, FT_VOFFSET);  // start of active screen
43
  ft800_memWrite16(REG_VSYNC0,  FT_VSYNC0);  // start of vertical sync pulse
44
  ft800_memWrite16(REG_VSYNC1,  FT_VSYNC1);  // end of vertical sync pulse
45
  ft800_memWrite8(REG_SWIZZLE,  FT_SWIZZLE);  // FT800 output to LCD - pin order
46
  ft800_memWrite8(REG_PCLK_POL, FT_PCLKPOL);  // LCD data is clocked in on this PCLK edge
47
  ft800_memWrite8(REG_CSPREAD,  FT_CSPREAD);  /* helps with noise, when set to 1 fewer signals are changed simultaneously, reset-default: 1 */
48
  // Don't set PCLK yet - wait for just after the first display list
49
50
  ft800_memWrite8(REG_ROTATE, 1);  // rotate display by 180°
51
52
  // Configure Touch
53
  ft800_memWrite8(REG_TOUCH_MODE, FT_TMODE_CONTINUOUS);  // enable touch
54
  ft800_memWrite16(REG_TOUCH_RZTHRESH, FT_TOUCH_RZTHRESH);  // Eliminate any false touches
55
56
  // Configure Audio - not used, so disable it
57
  ft800_memWrite8(REG_VOL_PB, 0x00);      // turn recorded audio volume down
58
  ft800_memWrite8(REG_VOL_SOUND, 0x00);    // turn synthesizer volume off
59
  ft800_memWrite16(REG_SOUND, 0x6000);    // set synthesizer to mute
60
61
  ft800_memWrite32(FT_RAM_DL, DL_CLEAR_RGB);
62
  ft800_memWrite32(FT_RAM_DL + 4, (DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG));
63
  ft800_memWrite32(FT_RAM_DL + 8, DL_DISPLAY);  // end of display list
64
  ft800_memWrite32(REG_DLSWAP, FT_DLSWAP_FRAME);
65
66
  ft800_memWrite8(REG_GPIO, 0x80);  // Enable the DISP signal to the LCD panel
67
  ft800_memWrite8(REG_PCLK, FT_PCLK);  // Now start clocking data to the LCD panel
68
69
  ft800_memWrite8(REG_PWM_DUTY, 70);  // Turn on backlight
70
  ft800_memWrite8(REG_INT_EN,1);      // włączam przerwana)
71
72
  DELAY_MS(10);  // just to be safe
73
  cmdOffset =ft800_memRead16(REG_CMD_WRITE);
74
}
75
76
///////////////////////////////////////////////////////////////////////////////////////
77
// kilka podstawowych funkcji do obsługi FT8xx
78
// atmega128
79
void init_spi(void)
80
{
81
  SPCR = (1<<SPE) | (1<<MSTR);  // SPI on, MSB first, Mode 0, Master, 
82
  //SPSR = (1<<SPI2X);      // Fosc/2 
83
  SPCR |= (1<<SPR0);        //     /16
84
}
85
void ft800_memWrite8(uint32_t ftAddress, uint8_t ftData8)
86
{
87
  ft800_cs_set();
88
  spi_transmit((uint8_t)(ftAddress >> 16) | MEM_WRITE); // Send Memory Write plus high address byte
89
  spi_transmit((uint8_t)(ftAddress >> 8));    // Send middle address byte
90
  spi_transmit((uint8_t)(ftAddress));    // Send low address byte
91
  spi_transmit(ftData8);      // Send data byte
92
  ft800_cs_clear();
93
}
94
void ft800_memWrite16(uint32_t ftAddress, uint16_t ftData16)
95
{
96
  ft800_cs_set();
97
  spi_transmit((uint8_t)(ftAddress >> 16) | MEM_WRITE); // Send Memory Write plus high address byte
98
  spi_transmit((uint8_t)(ftAddress >> 8));    // Send middle address byte
99
  spi_transmit((uint8_t)(ftAddress));    // Send low address byte
100
  spi_transmit((uint8_t)(ftData16));    // Send data low byte
101
  spi_transmit((uint8_t)(ftData16 >> 8));    // Send data high byte
102
  ft800_cs_clear();
103
}
104
void ft800_memWrite32(uint32_t ftAddress, uint32_t ftData32)
105
{
106
  ft800_cs_set();
107
  spi_transmit((uint8_t)(ftAddress >> 16) | MEM_WRITE); // Send Memory Write plus high address byte
108
  spi_transmit((uint8_t)(ftAddress >> 8));    // Send middle address byte
109
  spi_transmit((uint8_t)(ftAddress));    // Send low address byte
110
  spi_transmit((uint8_t)(ftData32));    // Send data low byte
111
  spi_transmit((uint8_t)(ftData32 >> 8));
112
  spi_transmit((uint8_t)(ftData32 >> 16));
113
  spi_transmit((uint8_t)(ftData32 >> 24));    // Send data high byte
114
  ft800_cs_clear();
115
}
116
void ft800_cmdWrite(uint8_t data)
117
{
118
  ft800_cs_set();
119
  spi_transmit(data);
120
  spi_transmit(0x00);
121
  spi_transmit(0x00);
122
  ft800_cs_clear();
123
}
124
// Beginn a co-processor command
125
void ft800_start_cmd(uint32_t command)
126
{
127
  uint32_t ftAddress;
128
129
  ftAddress = FT_RAM_CMD + cmdOffset;
130
  ft800_cs_set();
131
  spi_transmit((uint8_t)(ftAddress >> 16) | MEM_WRITE); // Send Memory Write plus high address byte
132
  spi_transmit((uint8_t)(ftAddress >> 8));  // Send middle address byte
133
  spi_transmit((uint8_t)(ftAddress));    // Send low address byte
134
  spi_transmit((uint8_t)(command));    // Send data low byte
135
  spi_transmit((uint8_t)(command >> 8));
136
  spi_transmit((uint8_t)(command >> 16));
137
  spi_transmit((uint8_t)(command >> 24));    // Send data high byte
138
  ft800_inc_cmdoffset(4);      // update the command-ram pointer
139
}
140
// virtually the same as ft800memWrite32() but calculating the address and offset as the other commands
141
void ft800_cmd_dl(uint32_t command)
142
{
143
  ft800_start_cmd(command);
144
  ft800_cs_clear();
145
}
146
//
147
void page_start(void)
148
{
149
  ft800_cmd_dl(CMD_DLSTART); // Start the display list
150
  ft800_cmd_dl(DL_CLEAR_RGB | GRAY_LIGHT2); // Set the default clear color 
151
  ft800_cmd_dl(DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG); // Clear the screen - this and the previous prevent artifacts between lists, Attributes are the color, stencil and tag buffers
152
}
153
//
154
void page_stop(void)
155
{
156
  ft800_cmd_dl(DL_DISPLAY);  // Instruct the graphics processor to show the list
157
  ft800_cmd_dl(CMD_SWAP); // Make this list active
158
  ft800_cmd_execute();
159
  _delay_ms(5);
160
  uint8_t int_mask = ft800_memRead8(REG_INT_FLAGS);
161
}
162
//
163
164
//przykładwe użycie:
165
const  uint8_t ds1307_daysinmonth [] PROGMEM = { 31,28,31,30,31,30,31,31,30,31,30,31 };
166
void ustaw_zegar(uint8_t minuty,uint8_t godziny,uint8_t dzien,uint8_t miesiac,uint8_t rok)
167
{
168
  uint8_t CurrTag=0,Pendown=0,PrevTag = 0, space;
169
  uint16_t tmp;
170
  btn_struct btn_s;
171
  char tmp_str[100];
172
173
  while(PrevTag!=TAG_OK && PrevTag!=TAG_CANCEL)
174
  {
175
    strcpy(tmp_str,num2string(2000+rok,NONE)); strcat(tmp_str,"/"); if(miesiac<10)  strcat(tmp_str,"0");
176
    strcat(tmp_str,num2string(miesiac,NONE)); strcat(tmp_str,"/"); if(dzien<10)  strcat(tmp_str,"0");
177
    strcat(tmp_str,num2string(dzien,NONE)); strcat(tmp_str,"  "); if(godziny<10)  strcat(tmp_str,"0");
178
    strcat(tmp_str,num2string(godziny,NONE)); strcat(tmp_str,":"); if(minuty <10) strcat(tmp_str,"0");
179
    strcat(tmp_str,num2string(minuty,NONE)); //strcat(tmp_str,":"); if(sekundy <10) strcat(tmp_str,"0");
180
    //
181
    if(!timDisp)
182
    {
183
      timDisp = 10;    
184
      page_start();  
185
      
186
      ft800_cmd_fgcolor(RED);
187
      ft800_cmd_gradcolor(RED);  //gradient przycisków
188
      ft800_cmd_dl(DL_COLOR_RGB | BUTTONS_TEXT_COLOR);    // kolor 
189
      
190
      ft800_cmd_ramfont(1, 34);
191
      ft800_cmd_dl(DL_COLOR_RGB | WHITE);  // kolor tekstu 
192
      ft800_cmd_text(800/2,200,1,FT_OPT_CENTERX|FT_OPT_CENTERY,tmp_str);
193
      
194
      space = 10; btn_s.w=(800-3*space)/2; btn_s.h=70; btn_s.y= 480-space-btn_s.h;
195
      btn_s.x=800-btn_s.w-space; btn_s.color=11141120; btn_s.tag=TAG_OK;
196
      draw_button_text2(btn_s,CurrTag,30,"ZAPIASZ");
197
      
198
      btn_s.color=2434341;  // ciemny szary
199
      btn_s.x=space;   btn_s.tag=TAG_CANCEL;
200
      draw_button_text2(btn_s,CurrTag,30,"ANULUJ"); //strcpy_P(tmp_str, txt[5+lng])
201
      
202
      ft800_cmd_dl(DL_COLOR_RGB | BLACK);  // kolor tekstu 
203
      space = 65; btn_s.w=180; btn_s.h=60; btn_s.y= 70;
204
      btn_s.x=30; btn_s.color=YELLOW; btn_s.tag=10;
205
      draw_button_text2(btn_s,CurrTag,31,"+");      
206
      
207
      btn_s.x+=btn_s.w+space+1; btn_s.w=70; btn_s.color=YELLOW; btn_s.tag=11;
208
      draw_button_text2(btn_s,CurrTag,30,"+");
209
      
210
      btn_s.x+=btn_s.w+space+10; btn_s.color=YELLOW; btn_s.tag=12;
211
      draw_button_text2(btn_s,CurrTag,30,"+");
212
      
213
      btn_s.x+=btn_s.w+space+5; btn_s.color=YELLOW; btn_s.tag=13;
214
      draw_button_text2(btn_s,CurrTag,30,"+");
215
      
216
      btn_s.x+=btn_s.w+space-3; btn_s.color=YELLOW; btn_s.tag=14;
217
      draw_button_text2(btn_s,CurrTag,30,"+");
218
      
219
      btn_s.w=180;btn_s.y= 270;
220
      btn_s.x=30; btn_s.color=YELLOW; btn_s.tag=15;
221
      draw_button_text2(btn_s,CurrTag,31,"-");
222
      
223
      btn_s.x+=btn_s.w+space+1; btn_s.w=70; btn_s.color=YELLOW; btn_s.tag=16;
224
      draw_button_text2(btn_s,CurrTag,31,"-");
225
      
226
      btn_s.x+=btn_s.w+space+10; btn_s.color=YELLOW; btn_s.tag=17;
227
      draw_button_text2(btn_s,CurrTag,31,"-");
228
      
229
      btn_s.x+=btn_s.w+space+5; btn_s.color=YELLOW; btn_s.tag=18;
230
      draw_button_text2(btn_s,CurrTag,31,"-");
231
      
232
      btn_s.x+=btn_s.w+space-3; btn_s.color=YELLOW; btn_s.tag=19;
233
      draw_button_text2(btn_s,CurrTag,31,"-");
234
      
235
      page_stop();
236
    }
237
      
238
    CurrTag = ft800_memRead8(REG_TOUCH_TAG);
239
    Pendown = ((ft800_memRead32(REG_TOUCH_DIRECT_XY)>>31) & 0x01);
240
    if(( 1 == Pendown) && (CurrTag != PrevTag))
241
    {
242
      if(PrevTag == 14){
243
        minuty++;
244
        if(minuty>59)minuty = 0;
245
      }
246
      if(PrevTag == 13){
247
        godziny++;
248
        if(godziny>23) godziny = 0;
249
      }
250
      if(PrevTag == 12){
251
        dzien++;
252
        if(dzien>pgm_read_byte(ds1307_daysinmonth + miesiac - 1)) dzien = 0;
253
      }
254
      if(PrevTag == 11){
255
        miesiac++;
256
        if(miesiac>12) miesiac = 1;
257
      }
258
      if(PrevTag == 10){
259
        rok++;
260
        if(rok>99) rok = 19;
261
      }
262
      if(PrevTag == 15){
263
        if(rok>19)rok--;
264
        else rok = 99;
265
      }
266
      if(PrevTag == 16){
267
        if(miesiac)miesiac--;
268
        else miesiac = 12;
269
      }
270
      if(PrevTag == 17){
271
        if(dzien)dzien--;
272
        else dzien = pgm_read_byte(ds1307_daysinmonth + miesiac - 1);
273
      }
274
      if(PrevTag == 18){
275
        if(godziny)godziny--;
276
        else godziny = 23;
277
      }
278
      if(PrevTag == 19){
279
        if(minuty)minuty--;
280
        else minuty = 59;
281
      }
282
      sygnal(100,1,1);
283
    }
284
    PrevTag = CurrTag;
285
  }
286
  // oczekiwanie na zwolnienie przycsiku
287
  while(!(ft800_memRead32(REG_TOUCH_DIRECT_XY)>>31) & 0x01){};
288
  if(PrevTag == TAG_OK)
289
  {
290
    tmp = ((minuty&0x3F)) | ((godziny&0x3F) <<6);
291
    send_tx_frame_wait(48,CMD_SET_TINE,tmp>>8,(uint8_t)tmp);  // wysyłam dane przez rs485 do innego modułu
292
    tmp = (dzien&0x1F) | ((miesiac&0x0F) << 5) | ((rok&0x3F) <<9);
293
    _delay_ms(50);
294
    send_tx_frame_wait(49,CMD_SET_DATE,tmp>>8,(uint8_t)tmp);  // wysyłam dane przez rs485 do innego modułu
295
  }
296
  _delay_ms(100);      
297
}

F_CPU=11059200 (is it to slow?)
Atmega 128, hardware SPI
PD=PINE6
CS=PINB4

Here are sch and pcb:
https://obrazki.elektroda.pl/2410018900_1582788848.png
https://obrazki.elektroda.pl/4933762200_1582788970.png

And movie:
https://filmy.elektroda.pl/54_1582790312.mp4

Regards,
Karol

von Rudolph (Gast)


Lesenswert?

Karol B. schrieb:
> There is a movie, didn't you saw it?

Yes, but apparently it played too small on the forum, I looked at it 
again and yes, it glitches.

> I have a lot of strange behavior of display. Its live on his own life,
> changing all elements on screen also pressing touch without physical
> finger touch.

Have you checked your 3.3V?
This displays draws current of 130mA or more on the 3.3V line.
I can not tell from the pictures which of the two 3.3V regulators is 
actually used for the display.
But, while I find no data for a LD117A, only LD1117A, the datasheet for 
the LD1117 lists 10µF minimum capacatiy at the output and you only have 
4.7µF.

And the APE8865-3 is designed to be stable with low ESR ceramic 
capacitors with 30mR to 50mR but it looks like you placed a tantalum cap 
there.
From what I can see in the video C12 at the display-connector also is a 
tantalum type.
Unless these are ultra low ESR types that might be the problem.

Annother idea, it looks like the case is made of metall and the 
anti-static bag under the display is a conductive one.
Please remove the display from the case and place it on a non-conductive 
underground.

>F_CPU=11059200 (is it to slow?)

This should be no problem.

I have to check the software later, looks like I need to translate some 
parts.

von Karol B. (karol_b135)


Lesenswert?

PCB has 2 options for 3.3V regulator (1117-33 or APE8865Y5) I use only 
1117 series (spx1117m3-l-3-3). 1uF on input nad 100nF+4uF7 (tantalum) on 
output.
I checked by powered up pcb from laboratory power suplyy, still the same 
issue on display. That's weird but screen callibration or built in logo 
are working fine.

I placeed display on a non-conductive underground.

I have the same program working on anbother PCB, there are only a little 
changes:
- CS=PINB5, PD=PINB4
- ATMEGA128A@5V + 74125 for SPI level shift

As you can see on scheamtic, my connections on no-working PCB are: 
CS=PINB4, PD=PINE6, ATmega128A@3.3V

von Rudolph (Gast)


Lesenswert?

Karol B. schrieb:
> I use only 1117 series (spx1117m3-l-3-3). 1uF on input nad
> 100nF+4uF7 (tantalum) on output.

So this is the one from Exar, what type exactly is the 4µ7 output 
capacitor?
What is the exact modell number or where did you order it from?

Karol B. schrieb:
> I checked by powered up pcb from laboratory power suplyy, still the same
> issue on display.

But you supplied 5V?

> That's weird but screen callibration or built in logo are working fine.

These are really simple commands, there is not much going over the SPI 
for these.

Karol B. schrieb:
> I have the same program working on anbother PCB, there are only a little
> changes:
> - CS=PINB5, PD=PINB4
> - ATMEGA128A@5V + 74125 for SPI level shift
>
> As you can see on scheamtic, my connections on no-working PCB are:
> CS=PINB4, PD=PINE6, ATmega128A@3.3V

This should work just fine.
11MHz should be well within the allowable frequence for 3.3V.
The only issue I could think of would be that PB0 is not set to output.

von Karol B. (karol_b135)


Lesenswert?

>4µ7 output capacitor? =>
TAJA475K006R from www.tme.eu

>But you supplied 5V?
Both, 5V+3.3V (3.3 LDO was present but current flow thrue it was equal 
or near 0mA)

I'm preaty sure now, the point is my pcb. The same program (only CS/PD 
pin connection are diferent) work fine on another PCB, but there are 
74xx125 level shifter.
Maybe the point is about SPI connection:
1) working fine => Atmega128@5V -> SPI thru 74LCX125MTC -> TFT
2) working bad => Atmega128@3.3V -> SPI direct to -> TFT
However, I saw on osciloscope shape of signals, they looks fine, I 
think.

PS. From some time, I allways set PB0 (SS) as output.
By the way, if it is an output, can I change state (PORTB0) in 
interrupt routine?

von Rudolph (Gast)


Lesenswert?

Karol B. schrieb:
>>4µ7 output capacitor? =>
> TAJA475K006R from www.tme.eu

Okay, this is the wrong capacitor for the job, the ESR is way too large.
Please replace it with a 4µ7 ceramic or put 2µ2+ in parallel to it.

>>But you supplied 5V?
> Both, 5V+3.3V (3.3 LDO was present but current flow thrue it was equal
> or near 0mA)

Hmm, okay.

> I'm preaty sure now, the point is my pcb. The same program (only CS/PD
> pin connection are diferent) work fine on another PCB, but there are
> 74xx125 level shifter.
> Maybe the point is about SPI connection:
> 1) working fine => Atmega128@5V -> SPI thru 74LCX125MTC -> TFT
> 2) working bad => Atmega128@3.3V -> SPI direct to -> TFT
> However, I saw on osciloscope shape of signals, they looks fine, I
> think.

I recently had an issue with an ATSAMC21 running at 3.3V and driving the 
SPI directly.
But that was because the ATSAMC21 is a lot weaker at driving the pins 
than the Mega128.
Also I was running the SPI at more than double the speed.
You could try to patch in a buffer for MOSI and SCK, something like a 
NC7WZ16P6X.
For MISO I am using a 74VHC1GT125 since I was hoping it would solve the 
issue that the data gets corrupted when reading with 24MHz - and it did 
not.

> PS. From some time, I allways set PB0 (SS) as output.

Excellent.

> By the way, if it is an output, can I change state (PORTB0) in
> interrupt routine?

Sure, this should not interfere with anything.

von Karol B. (karol_b135)


Lesenswert?

MISO line:
https://obrazki.elektroda.pl/6391929500_1582828139.jpg
The same shape is present on PCB with 74xx125 buffer.

I have built several new tiles, this is the rule - it works with buffer, 
and without buffer doesn't.

What's the matter? As you said, Atmega128 has enough Pin-current to 
drive directly SPI interface. Also, speed isn't to fast (now I slow 
down: SPCR |= (1<<SPR0| 1<<SPR1); @ F_CPU=11059200).

PS. I have tryed run new librarry. I changed SMAC21 project (create new 
one with ATmega128, slect TFT, set PD,CS lines and still have blank 
screen).

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

That on the MISO line is quite normal, if you plot CS with it this 
should happen very shortly after CS goes high.
The line is just not driven anymore.

Karol B. schrieb:
> As you said, Atmega128 has enough Pin-current to
> drive directly SPI interface.

I can not find it in the datasheet right now but the M128-A should be 
able to drive at least 10mA @ 3.3V while the C21 can drive at best 6mA 
with two dedicated high-current pins while all the other pins can only 
drive 3mA.
And the 6mA is not enough, I had to put a second pin-pair for SCK and 
MOSI in parallel to make it work - which of course is no option with the 
M128-A.

I will add a buffer to my design and that is hopefully the end of it.

And the worst part of that issue was that the display just crashed after 
a few seconds for no apparent reason.
The voltage levels looked totally fine to me.
I had a small filter with 10R and 22pF and did quite some measurements, 
nothing worked.
Then I just put two 741G125 buffers in the SCK and MISO lines and it 
worked up to maximum speed.

Annother issue I had before that was with a board that had a slightly 
unstable 3.3V.
It would flicker on startup and after a short time the touch-controller 
crashed.
On a hunch I changed three caps on the board, I put an extra cap in 
parallel to the ouput-cap of my stepdown, the switched the boost cap at 
this stepdown in case I put on the wrong part and I put a second cap in 
parallel at the input to the stepdown.
One of these, or two or all three together did the trick and that 
display is rock solid now.


Anyways, I put together a small test version for the M128-A that might 
be even working - it compiles fine but I can not test it.
The init_ports() function might need adjustment to play nice with your 
board.
Oh yes, and the profiling values are completely wrong due to that 
strange clock of 11.0592MHz.

von Ioan Mihai C. (mihaicozac)


Lesenswert?

Had this kind of self-tapping display error and found that the supply 
voltage was not stable enough, sometimes the current draw spikes and it 
leads to register corruption. Try with another power supply or use a 
extra ground wire from display to module, this helps also minimizing the 
audio noise if you use this function.

von Simon (Gast)


Lesenswert?

Hallo Rudolph,

auch von meiner Seite ein großes Dankeschön für deinen Treiber. Aktuell 
bin ich dabei diesen für meine Zwecke anzupassen. Dieser Thread hat mir 
bei einigen Problemen und Fragen zum BT-Chip weitergeholfen, allerdings 
bin ich jetzt auf ein Problem gestoßen, zu dem ich weder hier noch sonst 
wo etwas finden konnte.
Ich habe verschiedene Schriften konvertiert und auf den externen Flash 
gespielt. Das funktionierte bisher auch wie gewünscht.
Jetzt benötige ich allerdings verschiedene Symbole. Dafür habe ich mir 
die entsprechenden Schriften generiert, die diese Symbole beinhalten und 
die Symbole über UTF-8 Kodierung ausgegeben. Das funktioniert allerdings 
nur bis Codepage EF (Bsp.: E2 AF 85 zzgl. 0 zur Terminierung). Sobald 
die Symbole nach UTF-8 mit vier Bytes kodiert werden müssen (Bsp.: F0 9F 
A1 83 zzgl. 0 zur Terminierung), werden diese bei mir auf dem Display 
nicht mehr dargestellt.
Für die Darstellung der Schrift bzw. der Symbole verwende ich die 
EVE_cmd_text Funktion. Der Text wird allerdings nicht der Funktion 
übergeben, sondern vorher in einen entsprechenden Text-Buffer 
geschrieben. Diese Veränderung ist notwendig, um Abwärtskompaitbilität 
zur Software des vorherigen Displays gewährleisten zu können.

Codebeispiel:
1
switch (direction)
2
3
         {
4
            case 0://arrow up
5
            {
6
7
               arrow_x = x1+((x2-x1)/2)-20;
8
               arrow_y = y1+((y2-y1)/2)-12;
9
10
               EVE_cmd_setfont2(13, SPECIAL_FONT2_RAM_ADR,0); //special font
11
12
         //Dieser Pfeil wird korrekt dargestellt
13
               LCD_FuncData.text_buffer[0] =0xE2;
14
               LCD_FuncData.text_buffer[1] =0xAF;
15
               LCD_FuncData.text_buffer[2] = 0x85;
16
               LCD_FuncData.text_buffer[3] = 0;
17
               break;
18
            }
19
            case 1://arrow down
20
            {
21
               arrow_x = x1+((x2-x1)/2)-20;
22
               arrow_y = y1+((y2-y1)/2)-12;
23
24
               EVE_cmd_setfont2(13, SPECIAL_FONT2_RAM_ADR,0); //special font
25
26
         //Dieser Pfeil wird nicht angezeigt
27
               LCD_FuncData.text_buffer[0] =0xF0;
28
               LCD_FuncData.text_buffer[1] =0x9F;
29
               LCD_FuncData.text_buffer[2] = 0xA1;
30
               LCD_FuncData.text_buffer[3] = 0x83;
31
               LCD_FuncData.text_buffer[4] = 0;
32
               break;
33
            }
34
  }
35
36
  if (button_down)
37
        {
38
               EVE_cmd_button(x1,y1,x2-x1,y2-y1,13,EVE_OPT_FLAT); //hier wird die Beschriftung des Buttons über EVE_write_string aufgerufen und der Buffer-Inhalt an den BT816 übertragen
39
        }
40
        else
41
        {
42
               EVE_cmd_button(x1,y1,x2-x1,y2-y1,13,0);
43
        }

Vielleicht hat hier ja jemand eine Idee warum dieses Problem aufritt. 
Über einen Lösungsansatz würde ich mich freuen.

Grüße Simon

von Karol B. (karol_b135)


Lesenswert?

> von Ioan Mihai C:
I tried with another power supply with no effect. FPC between TFT module 
and my PBC is 10cm long (sometimes even 20cm long) also with no 
difference. I will try add some extra ground.
For now, I made 4 pcb extra with the same uC but also with 74x125  IC 
buffer. Its look terrible but is working :)

>Rudolph,
THX for EVE_Test_M128_RVT70.zip, I will try in few days (I hope today, 
I'm really cant wait for it :) )

von Rudolph R. (rudolph)


Lesenswert?

Simon schrieb:
> Ich habe verschiedene Schriften konvertiert und auf den externen Flash
> gespielt. Das funktionierte bisher auch wie gewünscht.
> Jetzt benötige ich allerdings verschiedene Symbole. Dafür habe ich mir
> die entsprechenden Schriften generiert, die diese Symbole beinhalten und
> die Symbole über UTF-8 Kodierung ausgegeben. Das funktioniert allerdings
> nur bis Codepage EF (Bsp.: E2 AF 85 zzgl. 0 zur Terminierung). Sobald
> die Symbole nach UTF-8 mit vier Bytes kodiert werden müssen (Bsp.: F0 9F
> A1 83 zzgl. 0 zur Terminierung), werden diese bei mir auf dem Display
> nicht mehr dargestellt.

Okay, interessant, so tief habe ich das noch nicht getestet.
Ich war ja schon froh, einfache Sonderzeichen benutzen zu können. :-)
Mein Font hatte auch nur so 242 Glyphen oder so.

Was Du mal ausprobieren kannst ist das Flash-Image in den EVE-Screen 
Editor zu laden, bei der .glyph den Haken rein, dass die ins RAM geladen 
wird, etwa gleich in Adresse Null.
Dann einfach nur noch das SETFONT2(13, 0, 0) dazu und
ein CMD_TEXT() in das Fenster ziehen mit eben dem Font.
Zumindest ein "µ" konnte ich problemlos benutzen, also Sonderzeichen 
gehen schon mal grundsätzlich.
Was ist F0 9F A1 83 überhaupt? :-)

Simon schrieb:
> {
>                EVE_cmd_button(x1,y1,x2-x1,y2-y1,13,EVE_OPT_FLAT); //hier
> wird die Beschriftung des Buttons über EVE_write_string aufgerufen und
> der Buffer-Inhalt an den BT816 übertragen
>         }

Simon schrieb:
> Für die Darstellung der Schrift bzw. der Symbole verwende ich die
> EVE_cmd_text Funktion. Der Text wird allerdings nicht der Funktion
> übergeben, sondern vorher in einen entsprechenden Text-Buffer
> geschrieben. Diese Veränderung ist notwendig, um Abwärtskompaitbilität
> zur Software des vorherigen Displays gewährleisten zu können.

Hmm, okay,  warum nicht einfach den String übergeben?

In meinem aktuellen Projekt steht sowas drin:
1
char str_output[128];
2
3
...
4
uint_to_str(calc, str_output, 4);
5
EVE_cmd_text(480+115, 195, 27, EVE_OPT_RIGHTX, str_output);
6
int_to_str_3(calc_int32, str_output, 2);
7
EVE_cmd_text(310+265, 355, 27, EVE_OPT_RIGHTX, str_output);
8
GetErrCodeText(u16_Ctrl_ErrCode_F1, str_output);
9
EVE_cmd_text(310, 450, 27, 0, str_output);

Die Funktion EVE_cmd_text() will ja nur einen Pointer haben.
Und abgesehen von der Null für das Ende und das nach 249 Zeichen gekappt 
wird ist der Funktion auch der Inhalt egal.

Karol B. schrieb:
> FPC between TFT module
> and my PBC is 10cm long (sometimes even 20cm long)

That might be the issue, I only use 5cm cables.
And maybe your layout, the display shares the SPI with the SD card 
socket.
With the controller in die middle and running the SPI lines left and 
right you may have an issue with reflections.
You could try and add small resistors in the lines, 10R perhaps.
But ultimately I would suggest switching to a controller that is a 
little more advanced than the Mega128A.
Even a Mega1281 would be an upgrade since it has two SPI.

von Simon (Gast)


Lesenswert?

Rudolph R. schrieb:
> Was ist F0 9F A1 83 überhaupt?

Das ist ein bestimmter Pfeil den ich gerne verwenden würde, also nicht 
so extrem wichtig. Ich bin mir aber nicht sicher ob ich ggf. später noch 
andere Symbole aus den entsprechenden Codepages benötige und versuche 
deswegen das Problem schonmal vorab zu klären.

Rudolph R. schrieb:
> Was Du mal ausprobieren kannst ist das Flash-Image in den EVE-Screen
> Editor zu laden

Das habe ich probiert und es sieht tatsächlich so aus, als könne der 
BT-Chip die 4-Byte codierten Pages nicht verarbeiten. Er hat alle 
Zeichen/Symbole unter der 4-Byte Grenze, die ich probiert habe 
problemlos angezeigt. Alles ab dieser Grenze wird nur noch mit zwei 
Fragezeichen dargestellt. Auf meinem realen Display wird gar nichts 
angezeigt.

von Rudolph (Gast)


Lesenswert?

Simon schrieb:
> Rudolph R. schrieb:
>> Was Du mal ausprobieren kannst ist das Flash-Image in den EVE-Screen
>> Editor zu laden
>
> Das habe ich probiert und es sieht tatsächlich so aus, als könne der
> BT-Chip die 4-Byte codierten Pages nicht verarbeiten. Er hat alle
> Zeichen/Symbole unter der 4-Byte Grenze, die ich probiert habe
> problemlos angezeigt. Alles ab dieser Grenze wird nur noch mit zwei
> Fragezeichen dargestellt. Auf meinem realen Display wird gar nichts
> angezeigt.

Poste das bitte mal hier: http://www.brtcommunity.com/
So nach dem Motto "melden macht frei".
Mal schauen, was Bridgetek dazu zu sagen hat.

Wichtig wäre noch irgendwie zu verifizieren, dass die Glyphen wirklich 
im Font enthalten sind, die könnten ja auch bei der Konvertierung schon 
verloren gehen.

Eine Möglichkeit wäre dann vielleicht noch die Glyphen direkt selber 
anzuzeigen.
Wenn Du im EVE Screen Editor unten mal das Tab "Inspector" auswählst 
siehst
Du was der aus den Kommandos macht.

Bei mir taucht mit zwei Zeichen gerade das hier auf:

  Raw  Text
11  0x0500000d  BITMAP_HANDLE(13)
12  0x1f000001  BEGIN(BITMAPS)
13  0x0182c1ce  BITMAP_SOURCE(0x800000 | 180686)
14  0x405a02d0  VERTEX2F(180, 720)
15  0x01819cf4  BITMAP_SOURCE(0x800000 | 105716)
16  0x410802d0  VERTEX2F(528, 720)

Also im Grunde zerlegt der Co-Prozesser für das CMD_TEXT den String und 
berechnet für jedes Zeichen die Position und welches Bild anzuzeigen 
ist.
Der Knackpunkt wäre die Adresse zu finden, die steht wohl in der .glyph 
drin.

von Simon (Gast)


Lesenswert?

Rudolph schrieb:
> Poste das bitte mal hier: http://www.brtcommunity.com/
> So nach dem Motto "melden macht frei".
> Mal schauen, was Bridgetek dazu zu sagen hat.

Ok mache ich im Laufe des Tages mal.

Rudolph schrieb:
> Wenn Du im EVE Screen Editor unten mal das Tab "Inspector" auswählst
> siehst
> Du was der aus den Kommandos macht.

Das habe ich gemacht und er macht aus meinem Pfeil tatsächlich zwei 
Fragezeichen:

Das ist meine Eingabe:
1
CMD_TEXT(123, 117, 13, 0, "??")

und das kommt dabei heraus:
  Raw  Text
13    0x01879bb4  BITMAP_SOURCE(0x800000 | 498612)
14    0x40f601d4  VERTEX2F(492, 468)
15    0x01879bb4  BITMAP_SOURCE(0x800000 | 498612)
16    0x411201d4  VERTEX2F(548, 468)
17    0x01879bb4  BITMAP_SOURCE(0x800000 | 498612)
18    0x412e01d4  VERTEX2F(604, 468)

Das merkwürdige ist, dass immer zwei Fragezeichen herauskommen, egal 
welches 4-Byte codierte Zeichen ich eingebe. Es scheint also von 
Bridgtek bewusst abgefangen zu werden....

von Rudolph R. (rudolph)


Lesenswert?

Kann man so einen Font irgendwo frei herunter laden um das mal 
auszuprobieren?

Und ich merke gerade das mir was Fonts angeht etwas die Tools fehlen.

Naja, für sowas wie "Prüfstand" habe ich das auch schon mal eingetippt 
und einen Screenshot davon gemacht. :-)

von Simon (Gast)


Lesenswert?

Rudolph R. schrieb:
> Kann man so einen Font irgendwo frei herunter laden um das mal
> auszuprobieren?

Der entsprechende Pfeil, der bei mir nicht funktioniert ist in dieser 
Schrift enthalten: 
https://fontlibrary.org/de/font/symbola#Symbola-Regular

Allgemein gibts es noch weitere nützliche Open Source Fonts, 
beispielsweise hier:
https://github.com/Microsoft/fonts
oder hier
https://github.com/adobe-fonts?page=1

von Rudolph (Gast)


Lesenswert?

Das ist ein wenig anstrengender als ich dachte. :-)

Der Pfeil ist also U+1F843, damit findet man den dann zum Beispiel auch 
in der Character-Tabelle zu dem Symbole Font.
In UTF-8 kodiert sind das die F0 9F A1 83 - was ja sofort offensichtlich 
im Zusammenhang steht. :-)

Nun ist 00000 bis 0FFFD der Bereich BMP - Basic Multilingual Plane.
Und 1F843 gehört zum nächsten Bereich SMP - Supplementary Multilingual 
Plane und ist da im Block "Supplemental Arrows-C".

https://www.sql-und-xml.de/unicode-database/#blockbereiche

Da wird in den BT81x wohl "nur" BMP implementiert sein.
Scheinbar hat das Windows Tool "Zeichentabelle" das gleiche Problem, da 
finde ich die Pfeile nämlich auch nicht.

von Rudolph (Gast)


Lesenswert?

Hast Du mal versucht den Offset der Glpyhe auszurechnen um diese direkt 
anzuzeigen?

Also wie hier:

11  0x0500000d  BITMAP_HANDLE(13)
12  0x1f000001  BEGIN(BITMAPS)
13  0x0182c1ce  BITMAP_SOURCE(0x800000 | 180686)
14  0x405a02d0  VERTEX2F(180, 720)

Im "BT81X Series Programminung Guide 1.1" steht auf Seite 100 / 101
wie man die die Adresse berechnet.

Dazu muss man die .glpyh auslesen.

Und dann im Kern sowas hier:

return (xf->start_of_graphic_data + xf->gptr[cp / 128] + bytes_per_glyph 
* (cp % 128) / 32);

Das hilft nur nicht, wenn die Daten gar nicht erst enthalten sind.

von Simon (Gast)


Lesenswert?

Rudolph schrieb:
> Da wird in den BT81x wohl "nur" BMP implementiert sein.

Das ist auch meine aktuelle Vermutung. Auf der BRT Seite hat sich leider 
noch nicht allzu viel getan, bin mal gespannt was da von Bridgtek als 
Antwort kommt.

Rudolph schrieb:
> Hast Du mal versucht den Offset der Glpyhe auszurechnen um diese direkt
> anzuzeigen?

Hatte ich noch nicht probiert. Habe das gestern auch nur kurz probieren 
können. Bei meinen errechneten Adressen ist der Screen Editor allerdings 
abgestürzt, obwohl der Adressbereich eigentlich gültig war. Ich gucke 
mir das bei Gelegenhiet nochmal in Ruhe an. Danke für den Tipp.

von Rudolph (Gast)


Lesenswert?

Ich habe mal ein wenig mit Fonts gespielt und mir fehlt vor allem immer 
noch ein Tool mit dem man Code-Blöcke aus Fonts löschen kann.
Über 8000 Glyphen zu haben ist zwar ganz nett, wenn man das auf Bitmap 
mit einer festen Größe konvertiert wird das aber schnell unlustig.

Der Webfont-Generator auf www.fontsquirrel.com ist schon sehr hilfreich, 
den finde ich von den Optionen her aber ein wenig eingeschränkt.
Und ich bin nicht mal sicher, ob der mit den Bereichen jenseits von BMP 
klar kommt.

Dann habe ich mir mal die resultierende .xfont Datei angesehen die der 
EVE Asset Builder erzeugt.
Und eine Sache ist schon mal sehr seltsam, die Anzahl der Glpyhen steht 
immer auf 65536, egal wie viele Glyphen der Font wirklich hat.

von Simon (Gast)


Lesenswert?

Bisher habe ich immer nur alle Glyphen oder eine so geringe Auswahl 
verwendet, dass ich die händisch in eine .txt-Datei geschrieben habe. 
Die kann man ja dann in den EVE Asset Builder laden als Vorgabe. 
Deswegen kann ich dir aktuell beim Thema Software zur Auswahl von 
Codeblöcken leider auch nicht weiterhelfen.

Rudolph schrieb:
> Dann habe ich mir mal die resultierende .xfont Datei angesehen die der
> EVE Asset Builder erzeugt.

Worin hast du dir die denn angesehen? In Notepad++ oder im hex-Editor 
kann ich da keine Rückschlüsse auf die Anzahl der Glyphen ziehen. Aber 
das würde ja die Vermutung bestätigen dass das einfach nicht vorgesehen 
ist.

von Rudolph (Gast)


Lesenswert?

Die .xfont habe ich einfach mit einem Hex-Editor aufgemacht.

Die Struktur dazu steht ja im Programming Manual.

Das sieht dann zum Beispiel so aus:

FF AA 00 01 Signatur
90 22 00 00 Size
B5 93 00 00 Format
4A 02 00 00 Swizzle
60 00 00 00 Layout Width
04 00 00 00 Layout Height
30 00 00 00 Pixel Width
14 00 00 00 Pixel Height
80 00 80 00 Start of Graphic Data
00 00 01 00 Number of Characters
00 2E 10 00 gptr - Offsets to glyph data

Anhand der Signatur sieht man, dass das erste Byte das LSB ist.

Die "Number of Characters" scheint dabei schon mal nicht richtig gesetzt 
zu werden, da steht immer 0x00010000 drin.

von Simon (Gast)


Lesenswert?

Ach stimmt da war ja was...

Rudolph schrieb:
> Die "Number of Characters" scheint dabei schon mal nicht richtig gesetzt
> zu werden, da steht immer 0x00010000 drin.

Habe das jetzt mal für verschiedene Schriften durchgeschaut und kann das 
nicht bestätigen. Bei mir variiert das je nach Anzahl enthaltener 
Zeichen (damit meine ich die Anzahl an Zeichen, die ich über die 
.txt-Datei vorgeben habe).
Auffällig ist allerdings dass der Wert immer kleiner oder gleich 65536 
ist. Bei der Symbolschrift, mit der ich die beschriebenen Probleme habe, 
steht der besagte Wert von 65536 drin.

von Rudolph (Gast)


Lesenswert?

Ich habe aktuell den Symbola.ttf mit den 8xxx Glyphen durch den EVE 
Asset Builder gezogen, ASTC, 12 Punkt, sowie einen Notosans-regular den 
ich mit Fontsquirrel auf 222 Glyphen reduziert habe.
Also einfach machen lassen ohne das über eine Datei einzuschränken.

Und da steht beide Male 0x00010000 drin.

Jetzt habe ich gerade mal den Notosans-regular mit 32xx Glyphen 
durchlaufen lassen und da ist das auch so.

von Simon (Gast)


Lesenswert?

Habe das auch nochmal ausprobiert. Dieser Wert scheint sich auf die 
Einschränkungen durch die .txt-Datei zu beziehen. Wenn ich den gesamten 
Schriftsatz konvertiere habe ich auch immer den Wert 0x00010000.

von Rudolph R. (rudolph)


Lesenswert?

Naja, mal davon ab, dass es dann eben nicht die Anzahl der Zeichen ist, 
das ist ja auch noch ein wenig niedrig angesetzt, so eigentlich.

Leider mahlen die Mühlen bei Bridgtek etwas sehr langsam und das hart 
moderierte Forum hilft da auch wenig diesen Eindruck zu entschärfen.

von Rudolph (Gast)


Lesenswert?

"We discovered an issue with EAB regarding 4-byte UTF-8 characters.
EAB v1.4 is scheduled at Mar 25 and will include a fix for this."

Na, das klingt doch sehr vielversprechend und lange hin ist das auch 
nicht mehr. :-)

Das interpretiere ich so, dass EVE das grundsätzlich kann, die Daten nur 
gar nicht erst durch den Konverter gegangen sind.

von Simon (Gast)


Lesenswert?

Ich bin auch positiv überrascht und werde das auf jeden Fall direkt 
testen, sobald die neue Software verfügbar ist. :-)

von JohnLemon (Gast)


Lesenswert?

Hello all,
I'm trying to figure out how to upload custom font to ram into BT815. I 
have Riverdi RVT43ULBNWC03 connected to ESP32 (arduino framework). I 
generated font files in EVE Asset Builder and tried to upload content of 
.raw file with EVE_cmd_loadimage command but display stuck on black 
screen... Can someone explain me how to upload fonts to BT81x?

von Rudolph R. (rudolph)


Lesenswert?

Well, do you also have a USB/SPI adapter like the Hermes board from 
Riverdi?
https://riverdi.com/product/hermes-board/

With that you can upload the flash image using the EVE Asset Builder to 
the on-board SPI-FLASH on the display.

In order to upload the data to EVEs G-RAM the font would need to be 
rather small.

Either way, EVE_cmd_loadimage() is only for .jpg and .png images.

You either need EVE_memWrite_flash_buffer() to transfer raw data from 
your target controller to G-RAM or EVE_cmd_inflate() if the data is 
z-lib compressed.

If you have the font data in the external SPI-FLASH you can use it 
directly from there if it is compressed in ASTC format.
In this case you only need to copy the .xfont file to G-RAM.
Preferably with EVE_cmd_flashread() as the .xfont can be stored in the 
SPI-FLASH as well.

When you have the .xfont in G-RAM and the .glyph either in G-RAM or in 
the SPI-FLASH you need to use EVE_cmd_setfont2() to assign a 
bitmap-handle to the new font.


What font are you using, how do you convert it and what sizes do the 
resulting files have?

: Bearbeitet durch User
von JohnLemon (Gast)


Lesenswert?

Hello Rudolph,
thank you for your answer. I don't have Hermes Board from Riverdi. I'm 
basing on AN277 from FTDI:
https://www.ftdichip.com/Support/Documents/AppNotes/AN_277_FT800_Custom_Font_Implement.pdf

I made .raw and .rawh files in EVE Asset Builder (Legacy Format), added 
content of metricblock and font table to my font.c file, and I tried to 
use it as in the AN277.
Is it possible to upload a font to FLASH via ESP32?

von Rudolph R. (rudolph)


Lesenswert?

Okay, so this is legacy format with a maximum of 128 characters.
You can just follow the application note then.
It would be possible to write the data to the SPI-FLASH but this would 
only make things more complicated.

The code in the application note has this:

//load font data into memory
Ft_Gpu_Hal_WrMemFromFlash(phost, RAM_G + 1000, 
SAMApp_ShowCustomFont_MetricBlock, 148);
Ft_Gpu_Hal_WrMemFromFlash(phost, RAM_G + 1000 + 148, 
SAMApp_ShowCustomFont_FontBmpData,
36432);

Translated to my library this is:

EVE_memWrite_flash_buffer(RAM_G + 1000, 
SAMApp_ShowCustomFont_MetricBlock, 148);
EVE_memWrite_flash_buffer(RAM_G + 1000 + 148, 
SAMApp_ShowCustomFont_FontBmpData,
36432);

When you have this up and running you can try to use setfont2 instead.
But not like in the application note.
I have no idea what the guys at FTDI where thinking when they did 
chapter 4.2 but it makes the example overly complicated by loading the 
data from a file instead of loading it from the controllers memory like 
in 4.1.
And loading a file from disk while building a display list also is not 
the brightest idea.

Also the example is plain wrong, the four lines before 
Ft_Gpu_CoCmd_SetFont2() are useless, Setfont2 takes care of this.
And the comment says that it sets the starting character to 32 but the 
parameter is "97".

I do not have an ESP32 here right now but a whole lot of displays 
including a Riverdi 4.3" and a Matrix Orbital EVE3-43G.

And to test this with an Arduino I could use the CFAF800480E1 from 
Crystalfontz which has a FT813.
See: 
https://github.com/RudolphRiedel/FT800-FT813/tree/4.x/example_projects/EVE_Test_Arduino_PlatformIO

Just change the target in platformio.ini , switch to EVE_RiTFT43 in 
EVE_config.h.
Then check the end of EVE_target.h for the Arduino options.
You need to provide the pins for Chip-Select and Power-Down.
And I am not sure about the ESP32, if the Arduino target provides a 
SPI.transfer() function the example already should compile and run just 
fine.

von Rudolph R. (rudolph)


Lesenswert?

Okay, I just went ahead and tried to build my Arduino example for ESP32.

platformio.ini:

[env:esp32]
platform = espressif32
board = wemos_d1_mini32
framework = arduino

EVE_target.h:

...
#if defined (ARDUINO)

  #include <Arduino.h>
  #include <stdio.h>
  #include <SPI.h>

  #define EVE_CS     9
  #define EVE_PDN    8
...

For some reason the ESP32 needs the Arduino.h include while it just 
builds for the Uno and the Due.

And then there are warnings that NOP() gets redefined in EVE.h.
So you can just comment out line 757 of EVE.h:
//#define NOP() ((45UL<<24))

With that it at least builds for ESP32.

von JohnLemon (Gast)


Lesenswert?

Hello,
thank you very much for your help. I will test it tomorrow. I know about 
warning with NOP and Arduino.h definitions. This is the case for every 
project.

von JohnLemon (Gast)


Angehängte Dateien:

Lesenswert?

Hello,
I bought Hermes and I uploaded the fonts to flash- it works perfectly 
:). But now I have problem with PNG without background.
I have a white icon (WIFI status) with background transparency. But when 
I display it on TFT I have icon in color that was previoulsy defined. 
When the color is the same like background where icon is, then it should 
be white, but it have color little bit darker than background.
1
drawBitmap(MEM_ICON_WIFI, 130, 3, 25, 25, EVE_RGB565, 0, WHITE);
1
void drawBitmap(uint mem_icon, uint x, uint y, uint w, uint h, uint fmt, uint tag, uint bg)
2
{
3
    EVE_cmd_dl(DL_COLOR_RGB | bg);
4
    EVE_cmd_dl(TAG(tag));
5
    EVE_cmd_dl(DL_BEGIN | EVE_BITMAPS);
6
    EVE_cmd_setbitmap(mem_icon, fmt, w, h);
7
    EVE_cmd_dl(VERTEX2F(x, y));
8
    EVE_cmd_dl(DL_END);
9
    EVE_cmd_dl(TAG(0));
10
}

von Vladislav N. (vladineufeld)


Lesenswert?

Hallo Rudolph,

ich würde mich freuen, wenn du mir weiterhelfen würdest.

Ich programmiere aktuell das EVE 3 7 Zoll Touchdisplay von Riverdi mit 
einem Nucleo STM32 Board. Dafür benutze ich die von Riverdi zur 
Verfügung gestellte Bibliothek in C.

Ich habe den EIndruck, dass ich leider das noch nicht ganz genau mit dem 
FIFO vom Grafikcontroller verstanden habe.

Jedenfalls habe ich mir folgenden Demo-Code gemacht:

        Gpu_CoCmd_Dlstart(phost);
        App_WrCoCmd_Buffer(phost, CLEAR_COLOR_RGB(0,0,255));
        App_WrCoCmd_Buffer(phost, CLEAR(1, 1, 1));
        App_WrCoCmd_Buffer(phost, BEGIN(BITMAPS));
        App_WrCoCmd_Buffer(phost, VERTEX2II(220, 110, 26, 'T'));
        App_WrCoCmd_Buffer(phost, VERTEX2II(244, 110, 26, 'E'));
        App_WrCoCmd_Buffer(phost, VERTEX2II(270, 110, 26, 'X'));
        App_WrCoCmd_Buffer(phost, VERTEX2II(299, 110, 26, 'T'));

        App_WrCoCmd_Buffer(phost, END());

        App_WrCoCmd_Buffer(phost, COLOR_RGB(160, 22, 22));
        App_WrCoCmd_Buffer(phost, POINT_SIZE(320));
        App_WrCoCmd_Buffer(phost, BEGIN(POINTS));
        App_WrCoCmd_Buffer(phost, VERTEX2II(192, 133, 0, 0));
        Gpu_CoCmd_Number(phost, 50, 100, 26,OPT_SIGNED, value);


   Gpu_CoCmd_Text(phost, 0,0, 26,0, "Hallo Welt");
   Gpu_CoCmd_Text(phost, 100,0, 26,0, "Hallo Welt");
   //Gpu_CoCmd_Text(phost, 200,0, 26,0, "Hallo Welt");
        //App_WrCoCmd_Buffer(phost, VERTEX2II(320, 110, 31, 'T'));

        App_WrCoCmd_Buffer(phost, END());
        App_WrCoCmd_Buffer(phost, DISPLAY());

        Gpu_Hal_WaitCmdfifo_empty(phost);
        App_Flush_Co_Buffer(phost);
        Gpu_CoCmd_Swap(phost);

Wenn ich den Code so ausführen lasse, dann sehe ich alle Elemente, die 
ich programmiert habe. Wenn ich jedoch eines der auskommentierten 
Befehle noch hinzufüge, bleibt der Bildschirm schwarz.

Weißt du, was das Problem sein könnte?

Mein erster Gedanke war, dass der FIFO voll ist. Das kann aber nicht 
sein, da das bei jedem Befehl gecheckt wird und so lange gewartet wird, 
bis genug Platz vorhanden ist und dann wird der Befehl erst 
reingeschrieben. Und ich habe es auch schon mit dem Debugger gecheckt: 
Es werden alle Befehle ausgeführt, nur rührt sich das Display nicht.

Viele Grüße

Vladi

von Rudolph R. (rudolph)


Lesenswert?

JohnLemon schrieb:
> drawBitmap(MEM_ICON_WIFI, 130, 3, 25, 25, EVE_RGB565, 0, WHITE);

That is your issue: EVE_ARGB1555
When you direclty load truecolor .png images they load as RGB565 - no 
alpha channel.
Either convert the images to ARG1555 and load them with cmd_inflate or 
even better since you already have the Hermes board now, use ASTC 
directly from the SPI-FLASH.
For example 8x8 which would be "EVE_COMPRESSED_RGBA_ASTC_8x8_KHR".

EVE_cmd_setbitmap(0x800000 | (adr_in_flash / 32), 
EVE_COMPRESSED_RGBA_ASTC_8x8_KHR, sizex, sizey);

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Vladislav N. schrieb:
> ich würde mich freuen, wenn du mir weiterhelfen würdest.

Ich kann es versuchen, aber...


> Ich programmiere aktuell das EVE 3 7 Zoll Touchdisplay von Riverdi mit
> einem Nucleo STM32 Board. Dafür benutze ich die von Riverdi zur
> Verfügung gestellte Bibliothek in C.

...ich habe weder richtig Erfahrung mit den Nucleo Boards, noch bin ich 
ein Freund der ersten Library von FTDI.
Einer der Gründe warum ich meine eigene Library geschrieben habe war, 
dass mich der Code von FTDI so gar nicht überzeut hat.

Die erste Frage wäre ja mal, welcher STM32?
Für die F4xx habe ich ja schon Support eingebaut und auch ein PlatformIO 
Projekt dazu das zumindest mal baut.

Vladislav N. schrieb:
> Ich habe den EIndruck, dass ich leider das noch nicht ganz genau mit dem
> FIFO vom Grafikcontroller verstanden habe.

Ich habe mir mal erlaubt ein .pdf von Crystalfontz anzuhängen, das 
findet sich in den Datenblättern von deren Displays.
Das ist zwar für die EVE2, aber ich fand das schon sehr anschaulich.

Vladislav N. schrieb:
> Weißt du, was das Problem sein könnte?

Das ist es, nur die beiden auskommentierten Zeilen?

Naja, das erste ist mal, BEGIN und END gehören Paar-weise zusammen.
1
 App_WrCoCmd_Buffer(phost, BEGIN(POINTS));
2
 App_WrCoCmd_Buffer(phost, VERTEX2II(192, 133, 0, 0));
3
 Gpu_CoCmd_Number(phost, 50, 100, 26,OPT_SIGNED, value);
4
 App_WrCoCmd_Buffer(phost, END());

Und dann ist die Zeile
 //App_WrCoCmd_Buffer(phost, VERTEX2II(320, 110, 31, 'T'));
so komplett aus dem Kontext gerissen.
Ohne das
App_WrCoCmd_Buffer(phost, BEGIN(BITMAPS));
machen VERTEX2II und VERTEX2F gar nichts.

Das VERTEX2II soll ja ein Bild anzeigen, 31 ist das Bitmap-Handle, 
vorbelegt durch einen Zeichensatz.
Und 'T' ist die Nummer 84, das 84. Bild aus dem Set, auch Zelle genann 
oder eben "cell".

Vladislav N. schrieb:
> Mein erster Gedanke war, dass der FIFO voll ist.

Der FIFO hat 4k, so leicht bekommt man den nicht voll. :-)

von Vladislav N. (vladineufeld)


Lesenswert?

Danke für die Datei. Die ist hilfreich!

Ich habe das Nucleo f20zfg (STM32 f2xx).

Ja wenn ich weiterhin nicht klar komme mit der Bibliothek, werde ich 
deine mal versuchen. Nur dann müsste ich den Code nochmal auf f2xx 
anpassen.

Ah ok ja stimmt das mit dem VERTEX Zeile ist wirklich ohne Zusammenhang 
^^
Aber das ist nicht das Problem. Diese auskommentierte Zeile können wir 
ruhig ganz ignorieren. Aber das Problem ist: Sobald ich das dritte 
"Hallo Welt" einkommentiere, dann wird gar nichts mehr angezeigt. Wenn 
ich das weglasse, dann werden die anderen Befehle problemlos angezeigt.

Was genau hat dir eigentlich nicht gefallen an der Bridgetek Bibliothek?

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Vladislav N. schrieb:
> Ja wenn ich weiterhin nicht klar komme mit der Bibliothek, werde ich
> deine mal versuchen. Nur dann müsste ich den Code nochmal auf f2xx
> anpassen.

Das habe ich gerade mal versucht und ein PlatformIO Projekt dafür 
aufgesetzt, analog zu dem F407 Projekt das ich schon hatte.

So wie es aussieht ist das HAL für den STM32F2xx komplett gleich zu 
benutzen wie das für den F4xx.

Ich habe in der EVE_target.h einfach nur den Block für den STM32F4 
kopiert und die Includes geändert.
Die größte Herausforderung war jetzt das richtige Define zu finden.
Die PlatformIO Board Dateien sind da hilfreich und so habe ich für das 
Nucleo_F207ZG schliesslich "#if defined (STM32F207xx)" gewählt.

Da müssen jetzt nur noch die Pins richtig angegeben werden.

Und wie beim letzten Projekt hier weiter oben, die main.c ist praktisch 
leer, das funktioniert so nicht, das ist nur um zu schauen ob es 
compiliert!

Warning This does compile but main.c does not work the way it is now!



Und schlau wäre auch in der EVE_target.c noch die entsprechenden 
Funktionen einzubauen um DMA machen zu können.
Nur benutze ich eben keine STM32 und zur Verfügung gestellt hat das 
bisher auch niemand.



Vladislav N. schrieb:
> Aber das Problem ist: Sobald ich das dritte
> "Hallo Welt" einkommentiere, dann wird gar nichts mehr angezeigt.

Hast Du das mit dem BEGIN/END denn gefixt?



Vladislav N. schrieb:
> Was genau hat dir eigentlich nicht gefallen an der Bridgetek Bibliothek?

Boah, so viele Ding und zu lange her. :-)
Aber wenn Du Dir nur mal die Zeilen ansiehst die Du gepostet hast, da 
taucht überall als Parameter "phost" auf.
Davon halte ich soweit gar nichts, das ist nämlich gar nicht für die 
Verwendung mit einem Mikro-Controller gedacht.
Anstatt das jedesmal wieder und komplett redundant zu übergeben habe ich 
den entscheidenden Parameter "cmdOffset" zu einer globalen Variable 
gemacht die auch absichtlich nur in der EVE_commands.c drin ist und 
nicht über die EVE_commands.h exportiert wird.

Und das ständige checken und noch mal checken des FIFOs bremst das ganz 
gut aus.

Meine Implementierung mag nicht ganz so robust sein, zum Beispiel könnte 
man den FIFO zu voll machen wenn man die Display-Liste erzeugt.
Aber wenn man das im Blick hat ist das komplett beherrschbar und so wie 
ich das implementiert habe deutlich schneller.
Das kostet ein paar kB extra, zugegeben.

Siehe auch das hier: http://www.brtcommunity.com/index.php?topic=100.0
Die neue "Portable MCU Library for EVE", beschrieben in BRT_AN_025 
gefällt mir deutlich besser als die erste Library von FTDI.
Wenn es das damals schon gegeben hätte, hätte ich meine Version 
vielleicht gar nicht angefangen.
Nur ist mein Code aktuell mit dem gleichen Controller eine ganze Ecke 
schneller.

Das was Riverdi in der Bibliothek gemacht hat ist auch deutlich 
aufgeräumter als die erste Implementierung von FTDI, viel leichter zu 
verstehen was da überhaupt passiert.
Ich bin allerdings sehr sicher, dass das langsamer läuft als meine 
Version.

von Vladislav N. (vladineufeld)


Angehängte Dateien:

Lesenswert?

Dankeschön,das hört sich gut an. Ich habe bislang noch nichts von 
PlatformIO gehört. Müsste mal ein neues Projekt in CubeIDE erstellen und 
die Dateien einfügen.

Ich habe jedenfalls gerade das Problem "behoben". Es sind gerade ganz 
verrückte Sachen passiert. Ich habe den Eindruck, der Grafikcontroller 
führt ein Eigenleben...

Ich bin auf die Idee gekommen, den Befehl 
Gpu_Hal_WaitCmdfifo_empty(phost) auszukommentieren. Dann hat die Anzeige 
plötzlich wie gewünscht geklappt. Auch etliche weitere Befehle wurden 
hinzugefügt und auch die problemlos angezeigt. Dann wollte ich mal beide 
Varianten mit dem Debugger vergleichen und mir den Befehl der wartet, 
bis der FIFO abgearbeitet wurde, genauer anschauen. Plötzlich ging die 
Anzeige auch als ich den Befehl einkommentiert hatte. Dann habe ich noch 
ein paar weitere Male das Programm draufgeflasht und alles war gut trotz 
des Befehls. Dann habe ich mal die Versorgungsspannung an und aus 
gemacht und dann ging es mit dem Befehl wieder nicht... oh ja Embedded 
Systeme sind manchnmal ganz komisch...
Jedenfalls denke ich, dass das nun der Fehler ist: Lieber 
Gpu_Hal_WaitCmdfifo_empty(phost) weglassen. Auch wenn ich nicht verstehe 
warum... Was ist das Problem? Dann wartet er eben noch bis der FIFO 
abgearbeitet wurde und erst dann wechselt er die Displayliste. Das war 
ja jetzt keine zeitkritisches Beispiel...(das Programm hat sich ja nie 
aufgehangen in ner Endschlosschleife, sondern wurde immer ganz 
durchgeführt.) Hast du als erfahrener Programmierer eine Erklärung? :D

Abgesehen davon: Warum wird eigentlich vom Hersteller im Datenblatt 
empfohlen, nicht direkt in die Displayliste zu schreiben, sondern den 
Umweg über den Co-Prozessor zu machen?
Was diesbezüglich komisch ist: Bei so einem Beispielprogramm von Riverdi 
wo ein Bildschirmschoner realisiert wurde (Ball baumelt von Ecke zu 
Ecke) haben die das nur mit direkten Befehlen in die DL gemacht...

Eine weitere Frage hätte ich auch noch: In der Riverdi Bibliothek kann 
man mit einem define auch noch eine "BUFFER_OPTIMIZATION" hinzuschalten. 
Ich habe mir mal den Code angeguckt und wenn man das aktiviert, dann 
werden die Befehle für den Co-Prozessor bzw. die DL-Befehle in einem 
extra Buffer gespeichert. Ich habe dir mal die entscheidenden vier 
Funktionen als Code im Anhang gepackt. Und mit den Befehlen 
App_Flush_Co_Buffer(phost); bzw App_Flush_DL_Buffer(phost); wird der 
Buffer dann komplett in RAM_CMD bzw. RAM_DL geschrieben. Wenn man das 
nicht aktiviert hat, dann wird jeder Befehl sofort in RAM_CMD bzw. 
RAM_DL geschrieben. Aber das komische ist: Wenn man diese Funktion 
aktiviert hat, dann passiert beides: Also dann wird beispielsweise durch 
den Befehl App_WrCoCmd_Buffer(Gpu_Hal_Context_t *phost,uint32_t cmd) 
sowohl der Buffer mit dem CMD gefüllt als auch sofort der CMD in RAM_CMD 
geschrieben. Und wenn man am Ende dann auch noch 
App_Flush_Co_Buffer(phost) schreibt, dann sind die Befehle ja doppelt in 
RAM_CMD.Einmal erst durch das direkte schreiben und danach nochmal nach 
schreiben des Buffer Inhalts. Ich weiß nicht ob das so gewollt? Eher 
nicht. Oder sollte man wenn man die BUFFER_OPTIMIZATION macht dann den 
anderen Codeteil der den Befehl direkt in den Speicher schreibt 
weglassen?
Was ich noch nicht erwähnt habe: Wenn man die die Funktion zuschaltet, 
dann wird auch geprüft, ob der Buffer schon voll ist. Wenn ja dann wird 
der komplette Inhalt direkt in den Speicher geschrieben

Jedenfalls liefen bei mir deren Demos stabiler als ich die 
BUFFER_OPTIMIZATION hinzugeschaltet habe (ohne hat es geflackert und mit 
gab es dann kein Flackern mehr).

Eine andere Sache noch:
Ich habe mit folgendem Programm, welches in der main() in der 
Dauerschleife läuft, versucht einfach mal die Touchkordinaten und den 
Tag Wert auf dem Bildschirm anzuzeigen:

void touchVersuch(Gpu_Hal_Context_t *phost, uint8_t* p_currTag, 
uint16_t* p_x_pos, uint16_t* p_y_pos)
{
  uint8_t tag = App_Touch_Update(phost, p_currTag, p_x_pos, p_y_pos);
  *p_currTag = tag;
  Gpu_CoCmd_Dlstart(phost);
  App_WrCoCmd_Buffer(phost, CLEAR_COLOR_RGB(0,0,255));
  App_WrCoCmd_Buffer(phost, CLEAR(1, 1, 1));
  Gpu_CoCmd_Number(phost, 0, 0, 26 ,OPT_SIGNED,*p_x_pos);
  Gpu_CoCmd_Number(phost, 0, 20, 26 ,OPT_SIGNED,*p_y_pos);
  Gpu_CoCmd_Number(phost, 0, 40, 26 ,OPT_SIGNED,*p_currTag);
  App_WrCoCmd_Buffer(phost, DISPLAY());
  //Gpu_Hal_WaitCmdfifo_empty(phost);
  App_Flush_Co_Buffer(phost);
  Gpu_CoCmd_Swap(phost);
}


Aber leider läuft das kaum. Nur zufällig mal. Mal kann ich mir die X 
Koordinaten anzeigen aber nach ner Zeit hängt es sich auf. Manchmal 
kommt direkt ein starres Bild, was sich durch Touch nicht mehr ändert. 
X- und Y Werte zusammen aktuallisieren klappt nie.
Weißt du das Problem?

von Rudolph R. (rudolph)


Lesenswert?

Um das noch mal zu erwähnen, ich bin für die Merkwürdigkeiten in der 
FTDI Library und auch der Variante davon von Riverdi ein wenig der 
falsche Ansprechpartner. :-)

PlatformIO, vor allem in Kombination mit VScode ist enorm praktisch um 
"mal eben schnell" ein Projekt für zig verschiedene Platformen 
aufzusetzen.
Zumindest solange es eine passende Board-Definition gibt.
CubeIDE habe ich gar nicht - und auch gar keine Verwendung dafür, weil 
ich mit den STM32 eben nichts anfangen kann.
Aber das Projekt da oben hat "stm32cube" als Framework.


Das mit dem Auskommentieren von Gpu_Hal_WaitCmdfifo_empty() ist 
merkwürdig.
Wie oft rufst Du den Display-Code eigentlich auf?
Das muss schon seltener passieren als die Bildrate vom Display ist.

Vladislav N. schrieb:
> Abgesehen davon: Warum wird eigentlich vom Hersteller im Datenblatt
> empfohlen, nicht direkt in die Displayliste zu schreiben, sondern den
> Umweg über den Co-Prozessor zu machen?

Wird das wirklich irgendwo empfohlen?
Der Co-Prozessor kann auf jeden Fall mehr und man muss auch weniger 
Daten übertragen, viele einfache Kommandos werden in mehrere Befehle in 
der Display-Liste zerlegt.

Spiel mal mit dem EVE Screen Editor.
Wenn Du da was von links in den Bildschirm ziehst, etwa ein "Text" dann 
taucht unten dazu auf was in den Co-Prozessor FIFO geschrieben wird.
Schaltet man dann den Tab unten auf "Inspector" um so sieht man was der 
Co-Prozessor da draus für Display-Listen Befehle macht.
Ein "einfacher" Button ist im Ergebnis doch ganz nett komplex.

Vladislav N. schrieb:
> Eine weitere Frage hätte ich auch noch: In der Riverdi Bibliothek kann
> man mit einem define auch noch eine "BUFFER_OPTIMIZATION" hinzuschalten.

Eigentlich nützlich ist sowas um den erzeugten Puffer dann anschliessend 
per DMA zu übertragen.
Optimiert ist das so in dem Sinne nur dadurch, dass beim Erzeugen des 
Puffers nicht auf das Ende der SPI-Übertragung gewartet wird.
Aber ob man nun Kommando-SPI-Kommando-SPI oder Kommando-Kommando SPI-SPI 
auführt ändert in Summe ja nichts an der Ausführungszeit.

Vladislav N. schrieb:
> Aber das komische ist: Wenn man diese Funktion
> aktiviert hat, dann passiert beides: Also dann wird beispielsweise durch
> den Befehl App_WrCoCmd_Buffer(Gpu_Hal_Context_t *phost,uint32_t cmd)
> sowohl der Buffer mit dem CMD gefüllt als auch sofort der CMD in RAM_CMD
> geschrieben.

Okay, das ist Unsinn, mit der Option an sollten die Kommandos nicht mehr 
direkt auf den SPI schreiben.

Vladislav N. schrieb:
> void touchVersuch(Gpu_Hal_Context_t *phost, uint8_t* p_currTag,
> uint16_t* p_x_pos, uint16_t* p_y_pos)
> {
>   uint8_t tag = App_Touch_Update(phost, p_currTag, p_x_pos, p_y_pos);
>   *p_currTag = tag;
>   Gpu_CoCmd_Dlstart(phost);
>   App_WrCoCmd_Buffer(phost, CLEAR_COLOR_RGB(0,0,255));
>   App_WrCoCmd_Buffer(phost, CLEAR(1, 1, 1));
>   Gpu_CoCmd_Number(phost, 0, 0, 26 ,OPT_SIGNED,*p_x_pos);
>   Gpu_CoCmd_Number(phost, 0, 20, 26 ,OPT_SIGNED,*p_y_pos);
>   Gpu_CoCmd_Number(phost, 0, 40, 26 ,OPT_SIGNED,*p_currTag);
>   App_WrCoCmd_Buffer(phost, DISPLAY());
>   //Gpu_Hal_WaitCmdfifo_empty(phost);
>   App_Flush_Co_Buffer(phost);
>   Gpu_CoCmd_Swap(phost);
> }

Das verwirrt mich jetzt doch mal, ich benutze das ja selber nie.
Aber ist das wirklich richtig, dass das "App_WrCoCmd_Buffer" mit 
"Gpu_CoCmd_Number" vermischt wird?
Muss wohl so, aber konsistent ist sowas nicht gerade.

Auf jeden Fall ist "App_Touch_Update()" wohl eher nicht so hilfreich.
Da passiert doch einfach mal zu viel drin.

Hilfreicher wäre da:
Gpu_Hal_Rd8(phost,REG_TOUCH_TAG);

Nur dazu müsstest Du in der Display-Liste überhaupt mal einen Touch-Tag 
vergeben und in dem Ausschnitt ist nichts.

Ohne Touch-Tag wäre das hier besser:
Gpu_Hal_Rd32(phost, REG_TOUCH_SCREEN_XY);

Und einfach mal mit cmd_number ausgeben.
1
void touch_test(Gpu_Hal_Context_t *phost)
2
{
3
 uint32_t koordinaten = Gpu_Hal_Rd32(phost, REG_TOUCH_SCREEN_XY);
4
5
 Gpu_CoCmd_Dlstart(phost);
6
 App_WrCoCmd_Buffer(phost, CLEAR_COLOR_RGB(0,0,255));
7
 App_WrCoCmd_Buffer(phost, CLEAR(1, 1, 1));
8
 Gpu_CoCmd_Number(phost, 20, 20, 28 , 0, koordinaten);
9
 App_WrCoCmd_Buffer(phost, DISPLAY());
10
 Gpu_CoCmd_Swap(phost);
11
 App_Flush_Co_Buffer(phost);
12
 Gpu_Hal_WaitCmdfifo_empty(phost);
13
}

Mir ist da am Ende noch aufgefallen das die Reihenfolge von 
App_Flush_Co_Buufer und Gpu_Hal_WaitCmdfifo_empty falsch herum war.
Und nachdem ich jetzt meinen Code eingefügt habe, habe ich noch die 
Position von dem SWAP Kommando verändert.


Bei mir würde das so aussehen:
1
void TFT_display(void)
2
{
3
 uint32_t koordinaten;
4
5
 koordinaten = EVE_memRead32(REG_TOUCH_SCREEN_XY);
6
7
 EVE_cmd_dl(CMD_DLSTART); /* start the display list */
8
 EVE_cmd_dl(DL_CLEAR_RGB | WHITE);
9
 EVE_cmd_dl(DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG);
10
 EVE_cmd_number(20, 20, 28, 0, koordinaten);
11
 EVE_cmd_dl(DL_DISPLAY);
12
 EVE_cmd_dl(CMD_SWAP); /* make this list active */
13
 EVE_cmd_start(); /* order the command co-processor to start processing its FIFO queue but do not wait for completion */
14
}

So etwas vereinfacht, normalerweise habe ich da noch ein 
EVE_start_cmd_burst() / EVE_end_cmd_burst() Paar drum herum.

von Vladislav N. (vladineufeld)


Angehängte Dateien:

Lesenswert?

Ah ok das ist ja praktisch mit PlatformIO!

Ja vieleicht könnte das wirklich ein Problem bei mir sein mit dem 
Timing. Denn damit kenne ich mich noch nicht so gut aus.

Das hier ist der Code, der automatisch von der Entwicklungsumgebung 
erzeugt wurde zur für die SystemClockConfiguration:

RCC_OscInitTypeDef RCC_OscInitStruct = {0};
  RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};

  /** Initializes the CPU, AHB and APB busses clocks
  */
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;
  RCC_OscInitStruct.HSIState = RCC_HSI_ON;
  RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI;
  RCC_OscInitStruct.PLL.PLLM = 13;
  RCC_OscInitStruct.PLL.PLLN = 195;
  RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2;
  RCC_OscInitStruct.PLL.PLLQ = 5;
  if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
  {
    Error_Handler();
  }
  /** Initializes the CPU, AHB and APB busses clocks
  */
  RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
  RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
  RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
  RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV4;
  RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV2;

  if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_3) != 
HAL_OK)
  {
    Error_Handler();
  }

Ich habe dann noch folgende paar Zeilen aus der Bibliothek von Riverdi 
inkludiert. Anschließend war die Anzeige stabiler (vorher war die 
Anzeige öfter mal zweigeteilt):

 /* configure the Systick interrupt time */
  HAL_SYSTICK_Config(HAL_RCC_GetHCLKFreq()/1000);

  /* configure the Systick */
  HAL_SYSTICK_CLKSourceConfig(SYSTICK_CLKSOURCE_HCLK);

  /* SysTick_IRQn interrupt configuration */
  HAL_NVIC_SetPriority(SysTick_IRQn, 0, 0);

   SystemCoreClock = 48000000; /* 48MHz */
   SystemCoreClockUpdate();

Also gehe ich maol davon aus, dass das Bild mit ner Frequenz von 48 MHz 
aktuallisiert wird.

So berechnet man dann die Bildrate des Displays:
800 x 480 = 384000  x 60 Hz x 24 Bit Auflösung = 552960000 Hz = 0,5 GHz

Der Aufruf ist also deutlich weniger als die Bildrate.
Oder habe ich jetzt irgendwas nicht verstanden?

Rudolph R. schrieb:
> Wird das wirklich irgendwo empfohlen?

Ja habe den Ausschnitt aus dem BT81x Programmierguide mal angehängt. 
Aber dort steht ja die Erklärung. Ist also nur eine Vorsichtsmaßnahme. 
Ah ok man hat also einfach mehr Möglichkeiten mit dem Co-Prozessor.

Später sollte ich mich auch mal mit DMA befassen. Aktuell ist es nicht 
in der Bib drinne aber habe gesehen, dass es von STM in der 
HAL-Bibliothek da Funktionen für gibt. Oder ich nutze deine Lib dann 
habe ich das schon :D Aber gut müsste bestimmt noch irgendwo mit den HAL 
Befehlen ergänzen.

Rudolph R. schrieb:
> Mir ist da am Ende noch aufgefallen das die Reihenfolge von
> App_Flush_Co_Buufer und Gpu_Hal_WaitCmdfifo_empty falsch herum war.
> Und nachdem ich jetzt meinen Code eingefügt habe, habe ich noch die
> Position von dem SWAP Kommando verändert.

Also das verstehe ich nicht, warum ist das falsch rum? Erst muss man 
doch die Anweisung geben, dass der Buffer in RAM_CMD geschrieben wird. 
Dann kann man mit Gpu_Hal_WaitCmdfifo_empty(phost); prüfen, ob das 
erledigt wurde (Also sind Lesezeiger REG_CMD_READ und Schreibzeiger 
REG_CMD_WRITE gleich ?). Und falls ja anschließend die Display Liste 
wechseln. Wo ist mein Denkfehler...?

Bist du dir sicher, dass der Code bei dir klappt mit dem Register 
REG_TOUCH_SCREEN_XY?
Bei mir hat es leider nicht funktuioniert. Also prinzipiell schon wenn 
man durchdebuggt. Aber nach ein paar Durchläufen hängt sich der Code auf 
nach dem Befehl: App_Flush_Co_Buffer(phost); Aber paar mal konnte ich 
wirklich den Registerwert auslesen und das wurde nach dem Swap Befehl 
dann angezeigt auf dem Display beim Debuggen. Scheint irgendein Problem 
mit dem Timing wohl zu geben...

Ja als nächstes werde ich mich mal mit dem EVE Screen Designer vertraut 
machen.

von Rudolph R. (rudolph)


Lesenswert?

Vladislav N. schrieb:
> Das hier ist der Code, der automatisch von der Entwicklungsumgebung
> erzeugt wurde zur für die SystemClockConfiguration:

Ja nun, ich habe gar keinen STM32. :-)

Vladislav N. schrieb:
> SystemCoreClock = 48000000; /* 48MHz */
>    SystemCoreClockUpdate();
>
> Also gehe ich maol davon aus, dass das Bild mit ner Frequenz von 48 MHz
> aktuallisiert wird.

Da draus geht bestenfalls hervor, dass Dein Controller mit 48MHz 
getaktet ist.
Kann man machen, nur läuft der STM32F207 mit bis zu 120 MHz.

>So berechnet man dann die Bildrate des Displays:
>800 x 480 = 384000  x 60 Hz x 24 Bit Auflösung = 552960000 Hz = 0,5 GHz

Äh, nein, die Bildrate wären die 60 Hz.
Aber die Bildrate sind auch nicht 60Hz, die ergeben sich aus dem 
Pixel-Clock.
Bei mir steht PCLK für dieses Display auf 2 und mit meiner Library sind 
das 36Mhz.
Wenn Riverdi da auch den Wert von 2 benutzt sind das entweder 30MHz oder 
eben auch 36MHz, je nachdem ob sie den Takt passend zu den BT81x 
einstellen.
Nun hat so ein Display nicht 800x480, das hat 1056 HCYCLE und 525 
VCYCLE.
Die Bildrate beträgt also so 65 Hz oder 54 Hz.
-> Zwischen zwei Updates sollten mindestens  18,5 ms sein.

Meine Software aktualisiert das alle 20 ms.

Interessant wäre an der Stelle dann auch noch, wie schnell überhaupt der 
SPI läuft.
Beim Init muss der nämlich langsamer als 11 MHz sein, danach darf der 
bis zu 30 MHz haben, das muss man aber erstmal stabil hin bekommen.

Vladislav N. schrieb:
>> Wird das wirklich irgendwo empfohlen?
>
> Ja habe den Ausschnitt aus dem BT81x Programmierguide mal angehängt.
> Aber dort steht ja die Erklärung. Ist also nur eine Vorsichtsmaßnahme.

Ah okay, das ist nur Quatsch, so wie das formuliert ist.
Der Co-Prozessor schreibt ja nicht einfach so aus Jux in die 
Display-Liste.
Richtiger wäre, dass es gefährlicher wird wenn man beides gleichzeitig 
versucht.

Vladislav N. schrieb:
> Also das verstehe ich nicht, warum ist das falsch rum? Erst muss man
> doch die Anweisung geben, dass der Buffer in RAM_CMD geschrieben wird.
> Dann kann man mit Gpu_Hal_WaitCmdfifo_empty(phost); prüfen, ob das
> erledigt wurde (Also sind Lesezeiger REG_CMD_READ und Schreibzeiger
> REG_CMD_WRITE gleich ?). Und falls ja anschließend die Display Liste
> wechseln. Wo ist mein Denkfehler...?

Nun ja, und wo wird dann auf die Ausführung von dem CMD_SWAP gewartet?

Die spannende Frage dazu ist schon mal, was macht App_Flush_Co_Buffer() 
eigentlich?

void App_Flush_Co_Buffer(Gpu_Hal_Context_t *phost)
{
#ifdef  BUFFER_OPTIMIZATION
    if (CmdBuffer_Index > 0)
    Gpu_Hal_WrCmdBuf(phost,CmdBuffer,CmdBuffer_Index);
#endif
    CmdBuffer_Index = 0;
}

So normalerweise, ohne diese "Buffer Optimisation" macht das praktisch 
garnichts weiter. Es wird auch automatisch jedes einzelne Kommando 
ausgeführt -> Handbremse.
Aber mit der "Buffer Optimisation" ist das der Befehl mit dem der 
CMD-FIFO beschrieben und das dann ausgeführt wird.
Lustigerweise beinhaltet das übrigens auch das Warten.

void Gpu_Hal_WaitCmdfifo_empty (Gpu_Hal_Context_t *host)
{
  while(Gpu_Hal_Rd16(host,REG_CMD_READ) != 
Gpu_Hal_Rd16(host,REG_CMD_WRITE));

  host->cmd_fifo_wp = Gpu_Hal_Rd16(host,REG_CMD_WRITE);
}

Okay, das macht was ich erwartet habe, wenn auch eher nicht so prall.
Wenn man REG_CMD_WRITE schon beschreibt weil man besser auch trackt wo 
der steht, dann muss man den  nicht lesen.
Und wenn man den schon liest, dann reicht einmal völlig aus...

In einem Beispiel von Riverdi habe ich das aber auch gerade so gefunden:
 App_WrCoCmd_Buffer(phost, DISPLAY());
 Gpu_CoCmd_Swap(phost);
 App_Flush_Co_Buffer(phost);
 Gpu_Hal_WaitCmdfifo_empty(phost);

Also das gehört schon so herum.

Vladislav N. schrieb:
> Bist du dir sicher, dass der Code bei dir klappt mit dem Register
> REG_TOUCH_SCREEN_XY?

Ja, habe ich gerade mal ausprobiert.
Allerdings habe ich dabei noch festgestellt, dass dem CMD_NUMBER noch 
eine Farbe fehlt:
 EVE_cmd_dl(DL_COLOR_RGB | BLACK);
 EVE_cmd_number(20, 20, 28, 0, koordinaten);

Und die Anzeige ist so alles anderes als nützlich, das gibt nur eine 
dicke Zahl.
Als Hex-Werte wäre das hilfreicher, oder eben wenn man die X/Y 
Koordinaten da raus zieht und getrennt ausgibt.
1
void TFT_display(void)
2
{
3
 uint32_t koordinaten;
4
 uint16_t x_koord, y_koord;
5
6
 koordinaten = EVE_memRead32(REG_TOUCH_SCREEN_XY);
7
 x_koord = (koordinaten >> 16);
8
 y_koord = koordinaten;
9
10
 EVE_cmd_dl(CMD_DLSTART);
11
 EVE_cmd_dl(DL_CLEAR_RGB | WHITE);
12
 EVE_cmd_dl(DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG);
13
 EVE_cmd_dl(DL_COLOR_RGB | BLACK);
14
 EVE_cmd_number(20, 20, 28, 0, x_koord);
15
 EVE_cmd_number(20, 40, 28, 0, y_koord);
16
 EVE_cmd_dl(DL_DISPLAY);
17
 EVE_cmd_dl(CMD_SWAP);
18
 EVE_cmd_start();
19
}

Das zeigt mir zwei Zahlen auf dem Display an, in Ruhe jeweils 32768 oder 
auch 0x8000 wie es im Programming-Manual steht.

Und wenn ich mit dem Finger über das Display gehen werden mir die 
Koordinaten angezeigt.
Das hat mich auch gerade darauf gebracht das mein Display schlecht 
kalibriert ist.
Ich habe einen leichten Versatz nach Rechts und etwas mehr nach Oben.

von Vladislav N. (vladineufeld)


Angehängte Dateien:

Lesenswert?

Puhh ich habe das mit den unterschiedlichen Clocks nun mal versucht 
nachzuvollziehen um PCLK herauszufinden und habe leider noch einiges an 
Verständnisproblemen.

Ich habe mal den Code und nachvollzogen und dort wird eine externe 
Quelle  als Taktversorgung eingesetzt(Weiß ich jetzt nicht, warum 
Riverdi nicht den internen relaxation oscillator clock benutzt).

Hier ist der Befehl:
Gpu_HostCommand(phost,GPU_EXTERNAL_OSC);

der ist mit 44h hinterlegt. Der Host Command 44h ist zum Festlegen der 
PLL.
"Select PLL input from external crystal oscillator or external input 
clock."

Laut Datenblatt kann man nur externe Quellen mit 12 MHz wählen, also 
gehe ich davon aus, dass die PLL nun 12 MHz ist.

Nun verstehe ich den Host Befehl CLKSEL nicht. Wann benutzt man denn 61h 
und wann 62h für das erste Byte?

Die benutzen bei der Initialisierung folgende Zeile:
Gpu_HostCommand(phost,GPU_PLL_48M)

GPU_PLL_48M ist mit 62h hinterlegt, also wird 620000h gesendet

Warum durch diesen Befehl die PLL auf 48 MHz setzen soll (so entnehme 
ich das dem typedef) erschließt sich mir nicht. Im Anhang ist die 
Bedeutung der Bits in Byte 2 zu sehen. Die sind ja alle 0.

"For compatibility to FT800/FT801, set Byte2 to 0x00. This will set the 
PLL clock back to default (60 MHz)"

Also laut dem Zitat wird die "PLL" auf 60 MHz gesetzt. Und nicht auf 48 
MHz?

Aber die eigentliche Funktion deises Befehl ist es ja, den Systemtakt 
festzulegen:
"Select the system clock frequency. Note that software shall also update 
the register value for REG_FREQUENCY to align with system clock 
selected."


In der Library habe ich auch noch folgende Funktion gefunden (die aber 
bei der Initialisierung nicht benutzt wurde):

Gpu_81X_SelectSysCLK (Gpu_Hal_Context_t  *host,
                      GPU_81X_PLL_FREQ_T  freq)
{
  if(GPU_SYSCLK_72M == freq)
    Gpu_HostCommand_Ext3(host, (uint32_t)0x61 | (0x40 << 8) | (0x06 << 
8));
  else if(GPU_SYSCLK_60M == freq)
    Gpu_HostCommand_Ext3(host, (uint32_t)0x61 | (0x40 << 8) | (0x05 << 
8));
  else if(GPU_SYSCLK_48M == freq)
    Gpu_HostCommand_Ext3(host, (uint32_t)0x61 | (0x40 << 8) | (0x04 << 
8));
  else if(GPU_SYSCLK_36M == freq)
    Gpu_HostCommand_Ext3(host, (uint32_t)0x61 | (0x03 << 8));
  else if(GPU_SYSCLK_24M == freq)
    Gpu_HostCommand_Ext3(host, (uint32_t)0x61 | (0x02 << 8));
  else if(GPU_SYSCLK_DEFAULT == freq)
    Gpu_HostCommand_Ext3(host, 0x61);
}

Da sie nicht benutzt wurde, gehe ich mal davon aus, dass der Systemtakt 
60 MHz ist.

In das Register REG_PCLK schreiben Sie in der Initialisierung den Wert 2 
rein, also denke ich mal, dass PCLK 30 MHz ist.


Rudolph R. schrieb:
> Die Bildrate beträgt also so 65 Hz oder 54 Hz.

Wie hast du die Bildrate berechnet?

Rudolph R. schrieb:
> Meine Software aktualisiert das alle 20 ms.

In welchem Teil deiner Library kann man das sehen, wie du das 
eingestellt hast?

Rudolph R. schrieb:
> Interessant wäre an der Stelle dann auch noch, wie schnell überhaupt der
> SPI läuft.
> Beim Init muss der nämlich langsamer als 11 MHz sein, danach darf der
> bis zu 30 MHz haben, das muss man aber erstmal stabil hin bekommen.

Woher hast du die Info, dass er langsamer als 11 MHz sein muss? Also du 
meinst bei der Initialisierung des Chips oder?

Ich habe jetzt übrigens mal diese

Vladislav N. schrieb:
> /* configure the Systick interrupt time */
>   HAL_SYSTICK_Config(HAL_RCC_GetHCLKFreq()/1000);
>
>   /* configure the Systick */
>   HAL_SYSTICK_CLKSourceConfig(SYSTICK_CLKSOURCE_HCLK);
>
>   /* SysTick_IRQn interrupt configuration */
>   HAL_NVIC_SetPriority(SysTick_IRQn, 0, 0);
>
>    SystemCoreClock = 48000000; /* 48MHz */
>    SystemCoreClockUpdate();

Ich habe überigens diese Befehle nun rausgenommen. Plötzlich 
funktionieren die Beispiele von Riverdi es auch ohne diese Befehle 
stabil. Also jetzt habe ich nur den Code für sie System Clock 
Configuration der automatisch von der IDE erzeugt wurde (Da werden dann 
auch die 120 MHZ benutzt :D)

Die Einstellungen des SPI habe ich graphisch über die IDE gemacht und da 
habe ich den Baudraten prescaler auf 2, was einer Baudrate von 30 Mbit/s 
entspricht. Die haben da nach so ein Beispiel wo das Bridgetek Logo 
angezeigt wird. Das läuft mit den 30 Mhz nicht ganz stabil. Da Habe ich 
herausgefunden, dass ein prescaler von 4 besser ist, also 15 MHz.

Aber mit beiden Frequenzen funktioniert das nicht mit der stabilen 
Anzeige der X und Y-Werte.

Es wird wohl bestimmt daran liegen, dass ich mir bislang noch gar keine 
Gedanken dazu gemacht habe, wie oft das Display aufgerufen wird und wie 
oft der Code in der Main aufgerufen wird. Erstmal wäre gut zu wissen, 
was für eine Bildrate eingestellt ist.
Und wie realisiere ich das, wie oft ein Code in der Main aufgerufen 
werden soll? Dafür muss ich mich wahrscheinlich über Timer informieren 
und dann vor den Code eine If Bedingung mit einer Timing Variablen 
machen und immer wenn der Timer die Variable setzt, dann erst den Code 
ausführen? (So wie du das in deiner Main gemacht hast). Aktuell wird der 
Code ja einfach wahrscheinlich mit den 120 MHz abgearbeitet und das ist 
ja viel schneller als die Bildrate...

von Rudolph R. (rudolph)


Lesenswert?

Vladislav N. schrieb:
> Ich habe mal den Code und nachvollzogen und dort wird eine externe
> Quelle  als Taktversorgung eingesetzt(Weiß ich jetzt nicht, warum
> Riverdi nicht den internen relaxation oscillator clock benutzt).

Naja, sie haben eben einen Quarz auf der Platine und mit diesem ist der 
Takt etwas stabiler.

Vladislav N. schrieb:
> Da sie nicht benutzt wurde, gehe ich mal davon aus, dass der Systemtakt
> 60 MHz ist.
>
> In das Register REG_PCLK schreiben Sie in der Initialisierung den Wert 2
> rein, also denke ich mal, dass PCLK 30 MHz ist.

Gut, das passt.

Vladislav N. schrieb:
>> Die Bildrate beträgt also so 65 Hz oder 54 Hz.
>
> Wie hast du die Bildrate berechnet?

30MHz / (1056 * 525) = 54,112554

Du hast bei Dir in der Formel noch 24 Bit Auflösung mit drin gehabt.
Die Daten werden allerdings parallel übertragen, nicht seriell.

Vladislav N. schrieb:
>> Meine Software aktualisiert das alle 20 ms.
>
> In welchem Teil deiner Library kann man das sehen, wie du das
> eingestellt hast?

In gar keinem, das ist Teil meiner Anwendung.
Die beiden Beispiele die ich auf Github habe machen das.
In dem ATSAMC21 Beispiel wird der Systick-Timer für einen 5 ms Interrupt 
verwendet damit die Hauptschleife nur alle 5 ms durchlaufen wird.
Und alle vier Durchläufe wird TFT_display() aufgerufen.
In dem Arduino Beispiel mache ich das gleiche, nur benutze ich da 
millis() um die Hauptschleife nur alle 5 ms auszuführen.

https://github.com/RudolphRiedel/FT800-FT813/blob/4.x/example_projects/EVE_Test_SAMC21_FT813_EVE2-35G/main.c

Vladislav N. schrieb:
> Woher hast du die Info, dass er langsamer als 11 MHz sein muss? Also du
> meinst bei der Initialisierung des Chips oder?

Ja, bei der Initialisierung des Chips.

Und das ist eine interessante Frage.
Im "FT800 Programmers Guide.pdf" steht noch im Kapitel 2.2.5: "Use MCU 
SPI clock not more than 11MHz".
Und im Kapitel 4.2.3 vom "DS_FT800.pdf" steht:
"If SPI is used as host interface, the SPI clock shall not exceed 11MHz 
before system clock is
enabled. After system clock is properly enabled, the SPI clock is 
allowed to go up to 30MHz."
Im Datenblatt vom FT81x findet sich das nicht mehr.
Im "FT81X_Series_Programmer_Guide_1.2.pdf" steht das im Kapitel 2.3 auch 
nicht mehr explizit drin, das Beispiel hat aber noch die Zeilen dafür.
Und im Kapitel 2.4 vom 
"BRT_AN_033_BT81X_Series_Programming_Guide_1.1.pdf" taucht nicht mal 
mehr das auf.

Hmm, interessant, sich daran zu halten ist jetzt nicht in dem Sinne 
falsch, aber scheinbar schon seit den FT81x so nicht mehr notwendig.

Das habe ich gerade mal ausprobiert.
Bis 17 MHz SPI Takt hoch kann ich den BT815 starten lassen.
Da drüber klappt es aber nur nicht mehr so richtig, weil ich noch ein 
Problem mit dem MISO habe und dann nur noch Murks über die Leitung 
kommt.
Mit 17MHz SPI Takt bleiben die X/Y Koordinaten auch nicht fest auf 
32768, da sind ständig Bit-Kipper drin.

Vladislav N. schrieb:
> Es wird wohl bestimmt daran liegen, dass ich mir bislang noch gar keine
> Gedanken dazu gemacht habe, wie oft das Display aufgerufen wird und wie
> oft der Code in der Main aufgerufen wird. Erstmal wäre gut zu wissen,
> was für eine Bildrate eingestellt ist.

(Sytem-Clock / PCLK) / (HCYLCE * VCYCLE)

Wobei man PCLK sinnigerweise so einstellt das sich in etwa 60 Hz 
ergeben.
Und nachdem ich das gerade in meine Excel-Tabelle für die 
Display-Parameter eingegeben habe, sollte ich vielleicht noch ein paar 
Parameter anpassen, da gerade viele von den kleinen Displays da deutlich 
drüber liegen.
Das EVE3-43G etwa das ich gerade benutze hat wie alle anderen 4.3" bei 
mir eine Einstellung von PCLK = 5, mit den 72MHz von dem BT815 macht das 
90Hz.
Ein PCLK = 7 und entsprechend 64 Hz wären sinnvoller.

Was man daran auch schön erkennen kann, die Framerate wird mit höheren 
Auflösungen zunehmend zum Problem, zumindest bis einschliesslich BT816.
Unter 2 sollte man gar nicht gehen, da EVE sonst Probleme bekommt die 
Pixel auch noch zu erzeugen.

Aber wenn man so eines wie das ADAM101 mit 1024x600 hat bei VCYCLE = 720 
und HCYCLE = 1100, da kommt man mit PCLK = 2 und den maximal 60 MHz des 
darauf verbauten FT813 eben nur auf 38 Bilder pro Sekunde.
Hätte das einen BT815 käme man wenigstens auf 45 FPS.

Deshalb gibt es auch (noch) keine EVE Displays mit etwa 1280x800.

von Vladislav N. (vladineufeld)


Angehängte Dateien:

Lesenswert?

Hallo,

ich habe mich mal einbisschen recherchiert über die Möglichkeiten die 
man mit EVE hat. Dabei bin ich auf das Beispiel 4 von dieser Seite 
gestoßen:

https://www.ftdichip.com/Support/SoftwareExamples/FT800_Projects.htm

So eine Anzeige wäre ziemlich cool für meine Endanwendung.

Natürlich gibt es den Code zu diesen Beispielen aber nur für andere 
Zielplattformen. Das Application Layer und das EVE Layer sind aber 
nahezu identisch wie auch in der Riverdi Bibliothek.

Ich habe versucht, den Code von der Datei "App_Gauges.c" in mein Projekt 
zu integrieren. Kompilieren hat dann auch geklappt, jedoch funktioniert 
die Anwendung leider nicht auf meinem Display.

Erst habe ich die Variable prog_uchar8_t digits[] aus "App_Gauges.c" nur 
in uchar8_t geändert. Denn in deren "platform.h" war das hier zu finden: 
#define prog_uchar8_t  uchar8_t
Keine Ahnung, warum die das gemacht haben aber das sollte ja nicht das 
Problem sein.

Die hatten in Ihrer Bibliothek noch die Funktion
Gpu_Hal_WrCmdBufFromFlash(...) drinne, welche ich auch einfach noch in 
meine Gpu_hal.c hinzugefügt habe.

Außerdem waren in deren Hal.utils.c noch folgende defines die ich 
hinzugefügt habe:
#define pgm_read_byte_near(x)   (*(x))
#define pgm_read_byte(x)        (*(x))
#define random(x)    (rand() % (x))

Wenn ich durch den Code debugge, dann hängt er sich irgendwann bei einem 
Gpu_Hal_WaitCmdfifo_empty(phost); auf.

Vieleicht liegt es aber auch daran, dass ich mich bislang noch gar nicht 
mit dem Flash Speicher des Riverdi beschäftigt habe, dieses Beispiel 
aber offenbar auch was mit Flash zu tun hat (wegen der Funktion 
Gpu_Hal_WrCmdBufFromFlash ). Das ist der Code der Funktion:

void Gpu_Hal_WrCmdBufFromFlash(Gpu_Hal_Context_t *host,uchar8_t 
*buffer,uint32_t count)

 uint32_t length =0, SizeTransfered = 0, getfreespace;
    do {
        length = count;
        getfreespace = Gpu_Cmdfifo_Freespace(host);
        if (length > getfreespace){
            length = getfreespace;
        }
        Gpu_Hal_CheckCmdBuffer(host,length);

        Gpu_Hal_StartCmdTransfer(host,GPU_WRITE,length);


        SizeTransfered = 0;
        while (length--) {
            Gpu_Hal_Transfer8(host,pgm_read_byte_near(buffer));
            buffer++;
            SizeTransfered ++;
        }
        length = SizeTransfered;

        Gpu_Hal_EndTransfer(host);
        Gpu_Hal_Updatecmdfifo(host,length);

        Gpu_Hal_WaitCmdfifo_empty(host);

        count -= length;
    }while (count > 0);

Aber hier ist ja als Flash dieses großen Zahlenarray aus "App_Gauges.c" 
gemeint. Was nicht klar ist, warum Gpu_Hal_Transfer8 benuitzt wird (hier 
erwartet man auch noch eine Antwort von der GPU die aber nirgendswo 
gespeichert wird)

Dort ist auch noch eine Schriftartendatei "digits.fon" (siehe Anhang). 
Aber ich habe nirgendswo in deren Code gesehen, wo Sie diese benutzen. 
Weißt du, was man mit der machen muss?

Hast du ne Idee, wie man das Beispiel zum Laufen bringen könnte?

Noch ne andere Sache: Dieser EVE Screen Designer, bringt der mir 
irgendwas wenn ich nicht eine von den supporteten Zielplattformen 
benutze? Nach dem Anschauen des Guides habe ich eher festgestellt, dass 
ich keinen Mehrwert erschließen kann, da ich ja nur den C-Code für 
andere Platformen bekommen kann.

Im ESD sind zwei Widgets die evtl. auch für mich in Frage kommen könnten 
(siehe die letzten beiden Anhänge). Aber diese findest man nicht im 
Programmierguide. Weißt du, wie es mir möglich wäre, diese Widgets 
einzubinden?

Der EVE Screen Editor hingegen kann mir helfen, da ich dort mal Sachen 
ausprobieren könnte, ohne sie kompilen zu müssen.

: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

Vladislav N. schrieb:
> Hast du ne Idee, wie man das Beispiel zum Laufen bringen könnte?

Äh, so spontan nicht, habe ich noch nicht versucht.
Gpu_Hal_WrCmdBufFromFlash() hat aber nichts mit dem SPI-FLASH auf dem 
Modul zu tun, das bezieht sich auf den Programm-Speicher vom Controller.
Sowas habe ich ja auch eingebaut, siehe oben, das stammt alles noch aus 
der Zeit vor den BT81x.

Den EVE Screen Designer benutze ich auch nicht.
Ich hoffe im Moment das dem EVE Screen Editor mal ein Exporter für die 
neue Library nach AN025 beigebracht wird, das ist dann schon mal viel 
dichter an meinem eigenen Code dran.

Was die Widgets angeht, zumindest das erste ist als Beispiel enthalten 
in dem aktuellen EVE Screen Editor.
Die Beispiele sind sowieso interessant, wenn auch etwas versteckt in dem 
Installations-Ordner.

: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

Hello,

yesterday evening I pushed a small update.
Among other things I marked the function EVE_get_touch_tag() as 
deprecated.
If you using it you will get a warning that it is deprecated.

Just use EVE_memRead8(REG_TOUCH_TAG); instead.
Or EVE_memRead8(REG_TOUCH_TAG1); and so in case of multi-touch.

And make sure EVE is not busy when you use DMA:
1
void TFT_touch(void)
2
{
3
  uint8_t tag;
4
  static uint8_t toggle_lock = 0;
5
  
6
  if(EVE_busy()) /* is EVE still processing the last display list? */
7
  {
8
    return;
9
  }
10
11
  tag = EVE_memRead8(REG_TOUCH_TAG); /* read the value for the first touch point */
12
13
  switch(tag)
14
  {
15
...


With the upcoming BT817 a couple more changes will be necessary.
The "#if defined (BT81X_ENABLE)" needs to be changed since BT817 
obviously still is a BT81x and yet it is beyond BT815 with additional 
registers.
Instead I am thinking about using "EVE2", "EVE3" and "EVE4".
EVE2 == FT81X_ENABLE
EVE3 == BT81X_ENABLE and EVE2 is to be set as well
EVE4 for BT817 with EVE3 and EVE2 to be set as well

Well, it may be time to make EVE2 base-line when the first BT817 
displays are released.
Meaning to finally remove FT80x support, clean it up some more and call 
it 5.x.

von Bernd Ickert (Gast)


Lesenswert?

Simple Frage an erfahrene Fachleute! Mit lang erprobter Hardware und 
Displays ab 4,3 Zoll (mind. 480x272) versuche ich nun schon seit Stunden 
ein 3,5 Zoll Display mit 320x240 zum Laufen zu bringen. Display-Treiber: 
FT813. Ist es möglich, dass dieser FT gar nicht für solche "kleinen" 
Displays vorgesehen ist? Hat der außer der Ober- auch eine 
Untergrenze???
Meine Erfahrungen zeigten, dass die Einstellungen der Register
HCYKLE  HOFFSET  HSYNC0 / HSYNC1 (und das Gleiche für V) recht 
großzügig in bestimmten Bereichen verändert werden können, ohne dass es 
sichtbare Auswirkungen hat.
Klar, HSIZE und VSIZE sollten wohl immer richtig sein (hier also 320 und 
240).
Zum Laufen bringen: Damit meine ich das Display einfach nur vollflächig 
mit einer Farbe beschreiben...
Je nach Einstellungen (an denen ich wie gesagt, nun schon seit Stunden 
probiere) habe ich angefangen von gar kein Bild bis zu halben/über Eck, 
flackernd die Hälfte, mit weißen Balken mal hier und da na usw...
Schließe ich einfach mal ein 480x272 an, habe ich ein grünes Bild (die 
Farbe, die es sein soll!) in der Größe 320x240 und weißem Balken 
unterhalb und "Farbschrott" rechts, was der Bereich > 320x240 ist!
Wo ist der Denkfehler?

Bernd

von Rudolph R. (rudolph)


Lesenswert?

Ich habe hier ein EVE2-35G liegen: 
https://www.matrixorbital.com/ftdi-eve/eve-ft812/eve2-35g

Das hat einen FT813, 3,5", 320x240 und spielt einwandfrei.
Ebenso das EVE3-35G mit dem noch dickeren BT815.

Mein Beispiel-Projekt ist für ein EVE2-35G konfiguriert:
https://github.com/RudolphRiedel/FT800-FT813/tree/4.x/example_projects/EVE_Test_SAMC21_FT813_EVE2-35G

Auf was für einer Hardware bist Du unterwegs, was für ein Display ist 
das genau und welche Timing-Einstellungen benutzt Du im Detail?

: Bearbeitet durch User
von Bernd Ickert (Gast)


Angehängte Dateien:

Lesenswert?

Ich bin  mit dem "niedlichen Platinchen" (siehe 18.1. diesen Jahres) 
unterwegs, also einfach nur den FT813, den ich per SPI bediene, so wie 
zuvor mit allen anderen Displays. Das 3,5' ist jetzt Premiere - und 
klappt nicht. Anbei das Datenblatt des Display. ACTRON, die mit dem 
einheitlichen 50-poligen Anschluss, weshalb ich einfach mal von einem 
Display zum anderen Wechseln kann.
Seite 18 findest Du die entsprechenden Timings für dieses Display. 
Kannst Du mir bitte, bitte sagen, welche Werte für HCYKLE  HOFFSET 
HSYNC0 / HSYNC1 (und V....) dafür erforderlich sind?!
REG_HSIZE = 320
REG_VSIZE = 240

Werte in Klammern dahinter, was ich schon alles u.a. probiert habe
REG_HCYCLE: 408 - 450 ???
REG_HOFFSET ? (40)
REG_SYNCO ? (20, 40, 0)
REG_SYNC1 ? (68, 48, 2, 1)
REG_VCYCLE: 262 - 350 ???
REG_VOFFSET ? (40, 30, 22
REG_VSYNC0 ? (10, 1 , 0)
REG_VSYNC1 ? (40, 18, 10)

REG_PCLK habe ich auch schon mal hochgesetzt (also Takt runter), derzeit 
auf 10, also 4,5MHz... Alles egal! Nur bei REG_PCLK = 1 geht nichts mehr 
(48 MHz), ab 2 geht es. Oder liege ich da falsch? Ich betreibe den FT813 
mit 12MHz-Quarz, also durch PLL 48Mhz. Wie hoch ist dann PCLK, wenn 
REG_PCLK = 1 ist? 48 oder 12 MHz (FOSC / 4) ???

Angebot "niedliches Platinchen" steht noch - wenn Du es brauchst!

von Bernd Ickert (Gast)


Lesenswert?

Nun ist mir noch etwas aufgefallen:
Im Datenblatt des Display 3,5' sind die Impulse (HSYNC / VSYNC) Positiv 
im Diagramm gezeichnet, während sie bei allen anderen (bisher von mir 
verwendeten) stets negativ sind und so auch im 
FT813-Programmieranweisung (s.28) aufgeführt sind, also auch negativ.
Außer die Polarität des Clock (mit REG_PCLK_POL) kann man aber die H- 
und V-Sync-Ausgänge nicht negieren. (?). Müsste man nun also die ganzen 
Zeiten (Anzahl CLK, Anzahl Lines) so umrechnen, dass sich eben die 
positiven Werte ergeben. Hattest Du so was schon mal?

von Rudolph R. (rudolph)


Lesenswert?

Okay, das ist also schon mal ein FT813.

Ist jetzt nicht so, als hätte ich mich damit schon oft herum schlagen 
müssen, normalerweise habe ich ja die Daten von den Modul-Herstellern.

Das Beste an den Timings ist ja, jeder Hersteller gibt das ein klein 
wenig anders an, mal ist der Buchstabensalat anders, mal fehlen auf den 
ersten Blick Werte.

Probier das mal:

#define EVE_HSIZE  (320L)
#define EVE_VSIZE  (240L)
#define EVE_VSYNC0  (0L)
#define EVE_VSYNC1  (4L)
#define EVE_VOFFSET  (22L)
#define EVE_VCYCLE  (262L)
#define EVE_HSYNC0  (0L)
#define EVE_HSYNC1  (20L)
#define EVE_HOFFSET  (88L)
#define EVE_HCYCLE   (408L)
#define EVE_PCLKPOL  (1L)
#define EVE_PCLK  (9L)

Die Clock-Polarität sagt ja nur, ob das nun auf die fallende oder auf 
die steigende Flanke zu beziehen ist.
Und nach dem Datenblatt ist es die fallende Flanke und somit 
REG_PCLK_POL=1.

Bernd Ickert schrieb:
> Ich betreibe den FT813 mit 12MHz-Quarz, also durch PLL 48Mhz.

Der hat aber per Default 60MHz, da muss man sich schon ein wenig Mühe 
geben den auf 48MHz runter zu bekommen. :-)

von Bernd Ickert (Gast)


Lesenswert?

Vielen Dank für die Daten! Das sind ja genau die, die lt. Datenblatt 
richtig sein sollten und mit denen ich (Plus/Minus) schon in allen 
Richtungen experimentiert hatte. Ich habe jetzt bei ACTRON ein neues 
geordert, um auszuschließen, ob es sich nicht doch um ein 
"Montags-"Display handelt. Wenn sich ein neues Display genauso verhält, 
wie dieses, na dann geht's weiter...

Ich betreibe den FT mit einem separaten Quarz 12MHz, so wie es im 
Datenblatt des FT813 in "Application Examples" vorgegeben ist. Was der 
FT dann mit dieser Frequenz noch macht, weiß ich (nicht) mehr. Ich 
meinte, mal gelesen zu haben, dass mit Hilfe der inneren PLL daraus dann 
48 MHz gemacht werden (beim PIC ist es jedenfalls so - einstellbar). 
Aber natürlich auch möglich, dass durch "Mal 5" - PLL daraus 60Mhz 
werden...
Ich melde mich wieder - Eine schöne Woche

von Bernd Ickert (Gast)


Angehängte Dateien:

Lesenswert?

Da haben wir (wahrscheinlich) das Problem. Nach Rücksprache mit ACRON 
mit einem sehr kompetenten Techniker (hat man selten bei 
Display-Lieferanten!!!) liegt das Problem an der DE-Polarität. Autor der 
beigefügten AppNote ist auch der, mit dem ich eben sprach. Auf Seite 10 
siehst Du in der Tabelle letzte Spalte von Unten das Aktive low für den 
DE, während alle anderen Aktive High sind. Und das kann der FT8xx nicht. 
Da das Problem bekannt ist, haben sie da schon was in petto und ich 
bekomme ein äquivalentes Display.
Dieses Muster kann ich aber auch noch durch Umlöten eines Widerstandes 
trotzdem verwenden. Anleitung dazu erhalte ich heute noch. Na dann mal 
sehen!!!

von Rudolph (Gast)


Lesenswert?

Doch, ja, ich bin mit den fertigen Modulen immer noch ganz glücklich 
soweit. :-)
Und ich bin schon gespannt was Matrix Orbital feines mit den BT817 raus 
bringen wird für EVE4.
Ich hoffe da auf ein EVE4-100G mit 10.1" und 1280x800. :-)

Bernd Ickert schrieb:
> Ich betreibe den FT mit einem separaten Quarz 12MHz, so wie es im
> Datenblatt des FT813 in "Application Examples" vorgegeben ist. Was der
> FT dann mit dieser Frequenz noch macht, weiß ich (nicht) mehr. Ich
> meinte, mal gelesen zu haben, dass mit Hilfe der inneren PLL daraus dann
> 48 MHz gemacht werden (beim PIC ist es jedenfalls so - einstellbar).
> Aber natürlich auch möglich, dass durch "Mal 5" - PLL daraus 60Mhz
> werden...

Das ist korrekt soweit, der Takt wird per PLL aus den 12MHz erzeugt.
Aber das mit den 48MHz war bei den FT80x der Fall, bei den FT81x waren 
das schon per Default 60MHz.
Bei den BT81x sind es per Default auch erstmal 60MHz, die lassen sich 
aber auf 72MHz hoch stellen - was meine Library auch macht.

von Mila Mik (Gast)


Lesenswert?

Rudolph schrieb:
> Doch, ja, ich bin mit den fertigen Modulen immer noch ganz glücklich
> soweit. :-)
> Und ich bin schon gespannt was Matrix Orbital feines mit den BT817 raus
> bringen wird für EVE4.
> Ich hoffe da auf ein EVE4-100G mit 10.1" und 1280x800. :-)

Ich warte seit Februar auf Muster vom BT817. Ich brauche den für eine 
Neuentwicklung wo ein Display mit 1024x600 gefordert wird. 
Seltsamerweise ist auf der Bridgetek-Seite jetzt wieder jeder Hinweis 
verschwunden, während der embedded war dort noch die Ankündigung. Weiß 
jemand wo die bei bridgetek dafür Zuständige Abteilung sitzt ? Ist das 
in UK oder Singapore ? Dürfen die noch arbeiten ?

von Rudolph R. (rudolph)


Lesenswert?

Ich hatte jetzt auch schon länger keinen direkten Kontakt mehr zum 
Support, aber das Forum läuft ja noch und das geht nur moderiert.
Eigentlich ja, dafür das im Februar der Release sein sollte sind die 
Informationen immer noch recht dünn.

So wie ich das verstehe, muss nicht stimmen, läuft das schon 
international.
Support auf jeden Fall aus UK.

Was die Entwicklung mit dem BT817 und dem 1024x600 Display angeht,
so wie ich das verstehe, kannst Du das im Grunde mit einem BT815 
anfangen.
Die dürften ziemlich kompatibel werden.
Die BT817 sind dann nachher schneller und erlauben eine höhere Bildrate.
Aber um das LVDS Interface kommt man wohl nicht herum, es sei denn 
Bridgetek nutzt die Zeit um den BT817 nach den Ankündigungen über das 
eine Bild zur Embedded World noch mal zu überarbeiten.
Meine letzten Informationen sind von Anfang März.

Das ADAM101 von Glyn ist übrigens ein 10.1" mit FT813 und 1024x600.
Da ist ein LVDS Chip drauf.
Der FT813 ist meiner Meinung nach mit dem Display aber ein klein wenig 
überfordert.

Edit: es gibt einen neuen EVE Asset Builder V1.4:
https://brtchip.com/eve-toolchains/#EVEAssetBuilder

Unter anderem sollen die UTF-8 Probleme gefixt sein.

: Bearbeitet durch User
von Simon (Gast)


Lesenswert?

Rudolph R. schrieb:
> Edit: es gibt einen neuen EVE Asset Builder V1.4:
> https://brtchip.com/eve-toolchains/#EVEAssetBuilder
>
> Unter anderem sollen die UTF-8 Probleme gefixt sein.

Ist mir auch schon aufgefallen und teste seit gestern. Habe die gleichen 
Tests gemacht wie bereits vor einigen Wochen beschrieben, aber das 
Problem ist unverändert da. Werde bei Bridgetek mal nach einem 
ESE-Beispiel inkl. Flashdaten fragen, mit dem es funktionieren soll.

von Rudolph R. (rudolph)


Lesenswert?

Was mich ein wenig wundert ist die Größe der Dateien.
Ich habe gestern noch mal eine gestrippte Version von dem 
notosans-regular auf 100 Punkte konvertiert.
notosans-regular-webfont_100_ASTC.glyph 3272kB

Okay, warum nicht, ist ja auch Mordsgroß.
Nur wenn ich diese Datei in eine .zip packe, dann schrumpft das zu 74kB.
Okay, der Font hat 222 Glyphen.
Also mal ein einzelnes Zeichen testen.
"1": 40kB - 581 Bytes als .zip
".": 8kB - 337 Bytes als .zip
"a": 96kB - 924 Bytes als .zip

So schlecht kann ASTC doch eigentlich gar nicht komprimieren?

Dazu die Release-Notes:
V1.4.0:
    - Fix bugs:
      + The UTF-8 code point 0xF09FA183 (i.e. 0x1F843 for unicode) 
cannot be displayed
      + The glyph file is not compressed when the code point is in UTF-8
      + eab_tools.exe will not run on a fresh 64-bit Win10 machine
      + Image conversion fail if current output folder does not exist
    - Add the "Verify" function in flash utility
    - Recognize UTF8-BOM and remove it before converting
    - Speed up generating font when code point mode is UTF-8
    - Replace 'numpy' by 'tinynumpy' to reduce distribution package size

Irgendwie sieht das danach aus als wäre bei der 1.4.0 nicht der 
Font-Converter für die 1.4.0 dabei.

Edit: "eab_tools font_convert -v" : EVE Font Conversion Utility V0.1.6

Mit der 1.4.0 habe ich exakt das gleiche wie mit der 1.2.0.

: Bearbeitet durch User
von Simon (Gast)


Lesenswert?

Klingt nach einer plausiblen Erklärung. Werde das im Bridgetekforum mal 
mit anklingen lassen :-)

von Mike T. (miket)


Lesenswert?

Rudolph R. schrieb:
> Das ADAM101 von Glyn ist übrigens ein 10.1" mit FT813 und 1024x600.
> Da ist ein LVDS Chip drauf.
> Der FT813 ist meiner Meinung nach mit dem Display aber ein klein wenig
> überfordert.

Danke, das kannte ich noch nicht. Im Datenblatt des BT815/FT813 steht 
eigentlich eine maximale Auflösung von 800x600, aber scheinbar geht dann 
ja auch mehr.
Wieso meinst du, dass man dann unbedingt LVDS braucht ? Das Display das 
ich anstrebe gibt es auch mit TTL Interface. Müsste das dann nicht 
direkt gehen ?
Noch einen LVDS-Transmitter dazu bauen wäre aber auch kein Problem.

von Rudolph R. (rudolph)


Lesenswert?

Mike T. schrieb:
> Danke, das kannte ich noch nicht. Im Datenblatt des BT815/FT813 steht
> eigentlich eine maximale Auflösung von 800x600, aber scheinbar geht dann
> ja auch mehr.

Das Maximum sind so theorethische 4096x4096 oder so.
Ist aber uninteressant, das Problem sind nicht die Pixel an sich.
Sondern der Pixel-Takt und dass das Bild ja auch noch erzeugt werden 
muss.
Mit dem ADAM101 lag ich glaube ich bei um 30 Bilder pro Sekunde.

> Wieso meinst du, dass man dann unbedingt LVDS braucht?

Na, unbedingt nicht, aber jenseits von 800x600 wird die Auswahl an 
Panels mit TTL Interfaces echt dünn.
Und LVDS stirbt auch schon wieder, MIPI DSI ist angesagt.

> Das Display das ich anstrebe gibt es auch mit TTL Interface.
> Müsste das dann nicht direkt gehen ?

Doch, das geht natürlich.

> Noch einen LVDS-Transmitter dazu bauen wäre aber auch kein Problem.

Das ist ganz schön hässlich im Layout, vor allem auch da die Signale 
vergleichsweise schnell sind.

von Mike T. (miket)


Lesenswert?

Rudolph R. schrieb:
> Das ist ganz schön hässlich im Layout, vor allem auch da die Signale
> vergleichsweise schnell sind.

Da muss man auf die richtige Impedanz (100Ohm differenziell, 50 Ohm 
single ended) und gleiche Länge der einzelnen Leitungen achten, dann 
geht das schon. Dafür sind es auch nur 4 oder 5 Leitungspaare also 10 
Leitungen und nicht 27. Hab ich schon oft gemach, funktioniert wenn mans 
richtig macht.

von Rudolph R. (rudolph)


Lesenswert?

Klar, geht das, keine Frage.
Und ich meinte jetzt auch mehr die andere Seite, also das TTL Interface 
an den LVDS Chip anzuklemmen.
Ich habe noch keinen LVDS Chip gesehen bei dem das einfach wäre, so mit 
TTL auf der einen Seite und LVDS+Versorgung auf der anderen Seite.
Irgendwie muss man immer 1/3 der Leitungen um den Chip herum wickeln.

Naja, ich werde sowas auch weiterhin nicht versuchen.
Gestern habe ich mal wieder nach Displays gefischt.
Über 800x600 und/oder über 7" gibt es praktisch nur welche mit LVDS.
Mit MIPI DSI habe ich jetzt gar nicht so viele gesehen.
Dann habe ich mit dem WF101FSYAPLNG0 ein nettes Teil gefunden mit dem 
man mal herum spielen könnte, nur kaufen kann man sowas dann natürlich 
nicht.
Aber naja, gibt eh kein richtiges Datenblatt einfach so frei dafür und 
der Aufwand dafür eine Platine zu machen steht auch in keinem Verhältnis 
zu dem Nutzen den ich davon hätte.

Das Spiel macht ohne Stückzahlen einfach keinen Spaß.

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Ich habe heute einen Test-Sockel auf ein EVE3-43G gelötet um mal einen 
Satz weiterer Flash-Chips zu testen.

http://www.brtcommunity.com/index.php?topic=77.msg318#msg318
1
Chip  Size(MBit)  Detect  Erase  Read/Write  CMD_FLASHFAST
2
W25Q128JVSIQ  128  Yes  Yes  Yes  Yes
3
SST26VF064BA-104I/SM  64  Yes  Yes  Write fails  -
4
AT25QF128A-SHB-T  128  Yes  Yes  Yes  0xE004 - device/blob mismatch
5
W25Q32JVSSIQ  32  Yes  Yes  Yes  Yes
6
W25Q64JVSSIQ  64  Yes  Yes  Yes  Yes
7
IS25LP128F-JBLE   128  Yes  Yes  Yes  Yes
8
S25FL064LABMFI010  64  Yes  Yes  Yes  Yes
9
S25FL128LAGMFV010  128  Yes  Yes  Yes  Yes
10
MX25L6433FM2I-08G  64  Yes  Yes  Yes  Yes
11
IS25LP064A-JBLE  64  Yes  Yes  Yes  Yes
12
AT25SF641-SUB-T  64  Yes  ?  Yes  0xE004 - device/blob mismatch

von Axel V. (axel-f)


Angehängte Dateien:

Lesenswert?

Gestern habe ich versucht, ein Bild anzeigen zu lassen.
Habe es zuerst mit dem "EVE Asset Builder" in ein ARGB1555 umwandeln 
lassen. Angezeigt wurde nur ein gelbes Rechteck (foreground colour). 
Dann habe ich es mit ARGB4 versucht- gleiches Ergebnis. Bildgröße war 
200 x 130. Dann habe ich eine andere Datei genommen, auf ARGB4 gewandelt 
und als 108 x 123 angezeigt. Das hat funktioniert.
Erst als ich das Ursprungsbild auf 50 x 33 verkleinert hatte, konnte ich 
es (als ARGB4) anzeigen. Ich hänge das Ursprungsbild mal an.
Gibt es da irgendwelche Größenbeschränkungen?
Zum Anzeigen habe ich aus Deinem Beispiel verwendet:
  FT8_cmd_dl(DL_BEGIN | FT8_BITMAPS);
  FT8_cmd_setbitmap(MEM_WOLKE, FT8_ARGB4, 50, 33);
  FT8_cmd_dl(VERTEX2F(240*16, 10*16));

Muß man hier irgendwie mit den Farben im Ursprungsbild aufpassen?

Danke,
Gruß Axel

von Axel V. (axel-f)


Lesenswert?

Oh, ich glaube ich hab's. Da war ganz am Anfang des Beitrags was von 
4k-Grenze zu lesen. An welcher Stelle ist die zu finden bzw. wodurch 
besteht diese Grenze?

Gruß Axel

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Ich habe das gerade mal in meinen Test-Code eingebaut und ich habe 
soweit keine Probleme mit der Anzeige in 200x130.
Das erste ist ARGB4, das zweite ist ARGB1555 und das dritte ist direkt 
als .jpg verwendet und entsprechend als RGB565 angezeigt.
Ach ja, das ist ein EVE3-50G.

Die Bilder habe ich mit dem EVE Asset Converter Builder 1.4.0 
konvertiert aus der hier angehängten Original Datei.
Option "Compressed" an und "Dithering" aus.

ARGB4: 5925 Bytes
ARGB1555: 9665 Bytes

Zwei Sachen sind mir aufgefallen.
Zum einen das oben angehängt Bild, das ist komplett "verseucht" mit 
Meta-Daten.
Wenn ich das in IrfanView aufmache wird mir angezeigt: JPEG, quality: 
90, subsampling ON (2x2)
Also habe das ohne Meta-Daten und mit 90% Kompression wieder 
gespeichert.

JPG: 5190 Bytes

Entweder ist die Angabe zur Kompression in der Original-Datei gelogen, 
oder da stecken wirklich über 40KiB Daten in der Datei die nichts mit 
dem Bild zu tun haben.
Ich habe das nicht nachgezählt, aber wenn man die Datei mit einem 
Hex-Editor aufmacht ist da Text drin ohne Ende.

Oh ja, schöner Test, packt man die Original-Datei in eine .zip, so hat 
das Archiv dann 17053 Bytes.
Packe ich die neue Datei in eine .zip werden das 5222 Bytes.


Zum anderen benutzt Du irgendeinen alten Stand aus 2018.

von Rudolph R. (rudolph)


Lesenswert?

Axel V. schrieb:
> Da war ganz am Anfang des Beitrags was von
> 4k-Grenze zu lesen. An welcher Stelle ist die zu finden bzw. wodurch
> besteht diese Grenze?

Das Problem besteht seit FT8_Commands.c Version 3.10 nicht mehr, also 
für cmd_inflate, für cmd_loadimage seit Version 2.7.
Die Ursache war, dass der Kommando-FIFO eben nur 4k groß ist und die 
Lösung war die Daten in Häppchen zu verschicken die kleiner als 4k groß 
sind.
Aus dem Grund ist in dem Zuge auch dazu gekommen, dass cmd_inflate nicht 
mehr "von Hand" ausgeführt werden muss, jedes Segment erfordert sowieso 
schon die Ausführung.

Aber ich bin mir gerade nicht mal sicher, ob in so einem Fall überhaupt 
was angezeigt worden wäre.

von Rudolph R. (rudolph)


Lesenswert?


: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

A little heads up, 5.0 will remove FT80x support.
But 5.0 will also support BT817/BT818 and since I do not even have a 
programming manual for EVE4 yet, do not hold your breath. :-)

von Vladislav N. (vladineufeld)


Lesenswert?

Hallo Rudolph,

haben die BT81X Chips Probleme dabei, große Grafiken darzustellen?
500x193 Pixel hat bei mir noch funktioniert. Aber bei 700x212 oder auch 
600x232 Pixel da wurde nur noch ein kleiner Teil des Logos dargestellt.

Mein aktuelles Vorgehen ist es, erst den Hintergrund des Logos zu 
entfernen und anschließend mit dem EVE Asset Builder zu komprimieren. 
Das Datenarray des komprimierten Logos speichere ich dann im Quellcode. 
Zur Übertragung des Arrays in RAM_G des Grafikcontroller nutze ich den 
inflate-Befehl. Dann sieht dann in etwa so aus:
....
Gpu_Hal_WrCmd32(phost,  CMD_INFLATE);
Gpu_Hal_WrCmd32(phost,  0);
Gpu_Hal_WrCmdBufFromFlash(phost,Logo_compressed, SIZE_COMPRESSED);

Gibt es eine Möglichkeit, größere Grafiken darzustellen?

Viele Grüße

Vladi

: Bearbeitet durch User
von Rudolph R. (rudolph)


Lesenswert?

Zufällig habe ich am Freitag erst mit größeren Bilder was ausprobiert.
Da ging es zwar darum ob der BT815 ASTC komprimierte Bilder aus dem 
RAM_G benutzen kann, dafür habe ich aber ein 1400x792 Bild auf ASTC 8x8 
komprimiert.
Das hat per zlib komprimiert 267664 Bytes und per cmd_inflate() entpackt 
sind es 277200 Bytes.

Das Bild ist übel chaotisch, soll glaube ich Kunst sein, im Grunde eine 
Farb-Explosion die in Kacheln zerlegt wurde welche zufällig verteilt 
sind.
Egal, ich habe mir eben bewusst ein Bild gesucht das schlecht 
komprimierbar ist.

Und das klappt ohne Probleme.
Selbst rotierend und gleichzeitig gezoomt.

Ach ja, das ist auf einem EVE3-50G, also mit 800x480.

Also dachte ich mir gerade mal so, machen wir EVE doch ein wenig Stress. 
:-)
https://www.nasa.gov/multimedia/imagegallery/image_feature_329.html

Okay, das Bild hat 3000x3000, das bekomme ich weder in den Speicher, 
noch dürfte der BT815 das anzeigen, weil das Limit meine ich so bei 
2048x2048 liegt.
Also habe ich erstmal den Rand etwas abgeschnitten und das dann in 
mehreren Stufen verkleinert bis ich endlich eine Datei hatte die in 
meinen ATSAME51J19A passt - der hat "nur" 512k FLASH. :-)
Bei 1440x1440 sind das 484178 Bytes als ASTC 8x8 und "compressed",
514800 Bytes im RAM_G nach cmd_inflate().

Funktioniert auch einwandfrei, sogar rotierend und mit Faktor 1,567 
vergrößert. :-)

Also an dem BT815 liegt es nicht.
Und meine Library macht das auch einfach so mit:
https://github.com/RudolphRiedel/FT800-FT813

Wobei ich ja zugeben muss, ich habe am Freitag die Parameter für die 
Länge der Daten bei cmd_inflate(), cmd_loadimage() usw. von uin16_t auf 
uint32_t angehoben.

Das sieht bei mir im Kern so aus:
1
EVE_cmd_setbitmap(MEM_PIC2, EVE_COMPRESSED_RGBA_ASTC_8x8_KHR, 1440, 1440);
2
3
EVE_cmd_dl(CMD_LOADIDENTITY);
4
EVE_cmd_rotatearound(720, 720, rotate, 1.234 * 0xffff);
5
EVE_cmd_dl(CMD_SETMATRIX);
6
7
EVE_cmd_dl(DL_BEGIN | EVE_BITMAPS);
8
EVE_cmd_dl(VERTEX2F(-420, 65));
9
EVE_cmd_dl(DL_END);
10
11
EVE_cmd_dl(RESTORE_CONTEXT());

von Vladislav N. (vladineufeld)


Lesenswert?

Rudolph R. schrieb:
 weil das Limit meine ich so bei
> 2048x2048 liegt.
> [/code]

Ok, jetzt bist du einen Anfänger eine Erklärung schuldig :D
Wie kann man denn Bilder mit 2048x2048 Pixeln oder so auf einem Display 
anzeigen, welcher nur eine Auflösung von 800 x 480 Pixeln hat?
Ich dachte, meine Bilder müssen kleiner als die 800x480 Pixel sein...

von Rudolph R. (rudolph)


Lesenswert?

Klar, komplett anzeigen ohne das zu verkleinern geht natürlich nicht 
größer als die Auflösung des Displays ist.

Aber da die Koordinaten von VERTEX2F mit Vorzeichen sind kann man einen 
beliebigen Ausschnitt aus dem Bild anzeigen.

Die Frage war ja, ob die BT81x mit großen Bildern klar kommen.
Und die Antwort ist, dass die sogar mit übertrieben großen Bildern kein 
Problem haben. :-)

Was natürlich nicht geht ist ein .jpg mit 1024x600 zu laden, nach 
cmd_loadimage() ist das schlicht größer als die 1MB RAM_G.
Aber in ASTC bekommt man sogar mehrere 800x480 Bilder gleichzeitig in 
das RAM_G.

von Vladislav N. (vladineufeld)


Lesenswert?

Moin,

benutzt du eigentlich SPI oder QSPI zur Kommunikation mit dem Display?

Ich mache gerade komischerwiese die Erfahrung, dass das Programm mit 
QSPI sehr instabil ist und sich schnell aufhängt, nachdem ich paar 
Nachrichten gesendet habe. Mit single SPI läuft alles perfekt. Kannst du 
dir das erklären? Am Code kanns wohl nicht liegen, da ich einfach die 
Bridgetek Bibliothek für den FT900 mC benutze.

Viele Grüße

Vladi

von Rudolph R. (rudolph)


Lesenswert?

Ich benutze rein SPI, QSPI habe ich bisher nicht mal ernsthaft in 
Erwägung gezogen.
Die einzige Verwendung die mir dafür einfällt wären Videos.

Bei den HMIs die ich mache müssen für das Display-Update alle 20ms so 
<2k übertragen werden, bei 4MHz SPI dauert das so 4ms.
Und mit DMA sind das 4ms in denen der Controller nicht mal beschäftigt 
ist.

Beim Startup könnte QSPI noch helfen wenn man viele Bilder zu kopieren 
hat.
Mein letzter Test war ein 4xxk Bild im ASTC Format anzuzeigen,
das beim Start zu übertragen hat ein wenig länger gedauert.
Nur mache ich Projekte vorzugsweise nur noch mit BT815 und entsprechend 
externem FLASH.

Entsprechend habe ich auch noch nicht versucht eine Platine für QSPI zu 
designen, obwohl ich mit dem ATSAME51J19 zum Beispiel einen Controller 
einsetze der ein QSPI Interface hätte.

von Mike T. (miket)


Lesenswert?

Falls die Info mal jemand benötigt :
Ich habe das ER-TFT101-1, ein günstiges 10,1" TFT mit 1024x600 und 
TTL-Schnittstelle von buydisplay.com an einem BT816 zum Laufen bekommen. 
Da im Datenblatt keine Angaben zum Timing stehen habe ich ne ganze Weile 
rumprobieren müssen. Hier sind die Displayeinstellungen die am Ende 
funktioniert haben ;

  wr32(REG_HCYCLE, 1232);
  wr32(REG_HOFFSET, 159);
  wr32(REG_HSIZE, 1024);
  wr32(REG_HSYNC0, 0);
  wr32(REG_HSYNC1, 1);
  wr32(REG_VCYCLE, 680);
  wr32(REG_VOFFSET, 23);
  wr32(REG_VSIZE, 600);
  wr32(REG_VSYNC0, 0);
  wr32(REG_VSYNC1, 1);
  wr32(REG_DITHER, 1);
  wr32(REG_PCLK_POL, 1);
  wr32(REG_PCLK, 2);//5
  wr32(REG_ROTATE, 0);
  wr32(REG_SWIZZLE, 0);

Vielleicht spart das ja jemandem ein bisschen Zeit.

von Rudolph R. (rudolph)


Lesenswert?

Danke, das ist interessant.
Auch wenn ich dafür eher keine Platine bauen werde.

Die Timing Werte erscheinen mir (wie gewohnt) seltsam zu sein, auch die 
Werte aus den Arduino Beispielen auf BuyDisplay.com:

#define HPW       70
#define HND       160
#define HDW       1024
#define HST       160
#define VPW       10
#define VND       23
#define VDH       600
#define VST       12
#define SCREEN_WIDTH 1024
#define SCREEN_HEIGHT 600

Das schon echt zum Schreien, macht man drei Datenblätter auf, selbst vom 
geichen Hersteller, bekommt man drei unterschiedliche Datensätze die auf 
verschiedene Art unvollständig sind.

Deine Timing Werte ergeben mit dem BT816 auf 72MHz übrigens 42,97 Hz.

von Vladislav N. (vladineufeld)


Lesenswert?

Rudolph R. schrieb:
> Bei den HMIs die ich mache müssen für das Display-Update alle 20ms so
> <2k übertragen werden, bei 4MHz SPI dauert das so 4ms.
> Und mit DMA sind das 4ms in denen der Controller nicht mal beschäftigt
> ist.

Wie kann man das berechnen mit den 4 ms?
Mit t = Datenmenge/Datenrate komme ich nicht auf den Wert

von Rudolph R. (rudolph)


Lesenswert?

Schauen wir mal, ob das passt. :-)
4 MHz sind 250ns pro Bit, 1 Byte in 2µs.
4ms / 2µs sind 2000

Puh, nicht verrissen. :-)

von Vladislav N. (vladineufeld)


Angehängte Dateien:

Lesenswert?

Ahh klar, das war nicht so schwierig. :D

Was hat das für einen Grund, dass dein SPI auf 4 MHz läuft, wobei 30 MHz 
möglich sind?

Hast du einen Tipp, wie man herausfinden kann, wie viele Daten bei jedem 
Neuladen des Bildes an das Display gesendet werden?
Ich habe jetzt mal den Code genommen und alle DL- und CMD-Befehle 
gezählt und komme bei der GUI im Anhang auf 372 Byte.
Muss ich da noch etwas beachten? (Klar, wenn ich Bilder einfüge, dann 
muss ich deren Speicherbedarf auch noch addieren)
Kann ich irgendwie herausfinden, wie groß meine Display Liste am Ende 
ist?

Und wird bei EVE eigentlich immer das gleiche Bild nochmal gezeichnet? 
Gibt es dort keinen Mechanismus, der das effektiver gestaltet, wie zum 
Beispiel Differenzkodierung? Also dass nur die Parts neu gezeichnet 
werden, die sich auch wirklich ändern?

von Rudolph R. (rudolph)


Lesenswert?

Vladislav N. schrieb:
> Was hat das für einen Grund, dass dein SPI auf 4 MHz läuft, wobei 30 MHz
> möglich sind?

Das war nur ein Rechenbeispiel, war wohl nur nicht ganz ausführlich 
genug.
Meine Software ist gerade so aufgebaut das ich alle 5ms den Touch polle 
und alle 20ms das Display aktualisiere.
Die main.c im meinen Beispielen zeigt die Details.
Die Test-Funktion testet ob das Display noch beschäftigt ist, die Update 
Funktion nicht.
Also um nicht einen Touch-Poll zu überspringen muss das Update in 
weniger als 5ms durch sein, daher die 4ms.
Die 2k sind auch eher ein Phantasie-Wert, beim letzten richtigen Projekt 
hatte ich deutlich weniger als das.

Die Frage war nach QSPI, meine Antwort war das ich sebst bei single-SPI 
mit nur 4MHz noch kein Problem hätte.

Mit den ATSAMC21 lasse ich den SPI bei 12MHz laufen, beim ATSAME51 bin 
ich bei 15MHz.
Beim AVR habe ich 8MHz genutzt.

> Hast du einen Tipp, wie man herausfinden kann, wie viele Daten bei jedem
> Neuladen des Bildes an das Display gesendet werden?
> Kann ich irgendwie herausfinden, wie groß meine Display Liste am Ende
> ist?

Meine Beispiel-Programme machen das.
Unten links werden vier Zahlen angezeigt.
Geschickte Bytes, die resultierende Länge der Display-Liste, wie lange 
das Display-Update gedauert hat in micro-Sekunden und die wie lange die 
Touch-Poll Funktion beschäftigt war.

Das habe ich beim Entwickeln einer Oberfläche immer irgendwo auf dem 
Screen.
Die CMD-FIFO Liste sollte ja unter 4k bleiben, aber vor allem muss die 
resultierende Display-Liste unter 8k bleiben.

> Und wird bei EVE eigentlich immer das gleiche Bild nochmal gezeichnet?
> Gibt es dort keinen Mechanismus, der das effektiver gestaltet, wie zum
> Beispiel Differenzkodierung? Also dass nur die Parts neu gezeichnet
> werden, die sich auch wirklich ändern?

Man kann Display-Listen vorberechnen, per cmd_memcpy() irgendwohin in 
RAM_G schieben und so ein Fragment dann beim Erzeugen der eigentichen 
Display-Liste per cmd_append() einfügen.
Mein Beispiel zeigt auch das, es gibt eine Funktion 
initStaticBackground() in welcher die statischen Elemente der Anzeige 
drin sind, das ist im Fall des Beispiels ein Rechteck am oberen Rand, 
ein Logo, eine schwarze Linie zum trennen und Text für die 
Debug-Ausgabe.

Im dynamisch erzeugten Teil wird das per cmp_append mit eingeklinkt, 
zusätzlich ein Button angezeigt, ein Bild das gedreht wird und die 
Zahlenwerte für die Debug-Ausgabe.

Das könnte man auch noch weiter treiben und mit kleineren Blöcken machen 
bei denen sich nur ein Detail verändert.
1
/* display a button */
2
EVE_cmd_dl(DL_COLOR_RGB | WHITE);
3
EVE_cmd_fgcolor(0x00c0c0c0); /* some grey */
4
EVE_cmd_dl(TAG(10)); /* assign tag-value '10' to the button that follows */
5
EVE_cmd_button(20,20,80,30, 28, toggle_state,"Touch!");
6
EVE_cmd_dl(TAG(0)); /* no touch */

Das braucht 32 Bytes, ein cmd_append braucht nur 12 Bytes.
Und das einzige was sich da ändert ist der Wert von "toggle_state" und 
auch nur mit zwei Werten.
Mit könnte also zwei Fragmente erzeugen und mit der Variable entscheiden 
welche man anhängt, das wären dann 20 Bytes weniger pro Update.

Oder man lässt es, weil man die Daten sowieso per DMA überträgt. :-)
Oder man setzt sich ein Limit von z.B. 1ms die das alles dauern darf und 
fängt erst mit trickreicheren Optimierungen an wenn man das reisst.

Da hört das auch noch nicht auf, was zum Beispiel auch was bringen kann 
ist die Kommandos so zu sortieren das weniger redundante Kommandos 
geschickt werden.

Wenn man zum Beispiel 16 Icons hat die rot grün oder blau sein können 
macht es mehr Sinn drei Blöcke für rot grün und blau zu haben als für 
jedes einzelne Icon die Farbe zu senden.
Das zieht zwar den Code im Controller auseinander, dafür hat man dann 
aber nur noch drei Farb-Kommandos statt 16.

von Vladislav N. (vladineufeld)


Lesenswert?

Ah ok, interessant :)
Rudolph R. schrieb:
> Mit den ATSAMC21 lasse ich den SPI bei 12MHz laufen, beim ATSAME51 bin
> ich bei 15MHz.
> Beim AVR habe ich 8MHz genutzt.

wie kommen diese Werte zustande? Wie hast du ermittelt, dass sie am 
optimalsten sind?

Ich habe stelle mir gerade die Frage, welche SPI-Frequenz ich verwenden 
sollte. Ich muss MQTT-Daten (aktuelle Geschwindigkeit des Fahrzeugs) auf 
dem Bildschirm darstellen. Aktuell habe ich einen Task, welcher alle 100 
ms den MQTT-Buffer pollt und einen weiteren task, der alle 250 ms die 
Funktion aufruft, welche das Display neu zeichnen lassen soll. 
Eigentlich reicht es ja, die Fahrzeug-Daten 4 Mal pro Sekunde zu 
aktuallisieren sodass sich der Geschwindigkeitsbalken in Echtzeit 
aktuallisiert ^^
Nun habe ich berechnet, dass 30 MHz SPI 0,1 ms brauchen, um die 
EVE-Daten zu übertragen. Mit 1 MHz SPI würde das ganze 3 ms dauern. Also 
eigentlich könnte ich ja problemlos eine sehr geringe SPI Frequenz 
nehmen.

Sollte ich das tun? Das hat doch dann den Vorteil, dass der Strom durch 
das System geringer ist und dass das schonender für die Bauteile ist 
oder? ^^
Oder hast du einen Rat, welche Frequenz ich nehmen sollte.
Letzten Endes ist es egal aber ich will auch ne schöne Argumentation in 
meine Bachelor-Doku schreiben :D

von Rudolph R. (rudolph)


Lesenswert?

Vladislav N. schrieb:
>> Mit den ATSAMC21 lasse ich den SPI bei 12MHz laufen, beim ATSAME51 bin
>> ich bei 15MHz.
>> Beim AVR habe ich 8MHz genutzt.
>
> wie kommen diese Werte zustande? Wie hast du ermittelt, dass sie am
> optimalsten sind?

Das sind nicht die "optimalsten" Werte, das sind die schnellsten Werte.
Beim AVR geht nicht mehr als 8MHz und da der kein DMA kann geht die 
Datenübertragung voll mit ein in die Zeit für die Aktualisierung.

Der ATSAMC21 läuft mit 48MHz, hat nur eine PLL und die Frequenz wird 
eingestellt mit der Formel: Clock / (2 * (BAUD + 1))
BAUD 0: 24MHz
BAUD 1: 12MHz
BAUD 2: 8MHz
BAUD 3: 6MHz

Bei 24MHz funktioniert nur der Touch nicht mehr mit meiner Hardware.
Ich vermute wegen der Laufzeit der Gatter die ich zwischen Controller 
und Display habe.

Beim ATSAME51 ist es im Grunde das gleiche, nur füttere ich da (nicht 
ganz nach Spec) 120MHz in den SPI und komme mit einem BAUD Wert von 3 
auf 15MHz.
Bei einem Wert von 4 und entsprechend 20MHz funktioniert der Touch nicht 
mehr.

Die Anzeige an sich ist auch mit viel schnellerem SPI stabil.

Benötigt wird das nicht wirklich und ich nutze mit beiden ATSAM DMA, 
also könnte ich den SPI auch langsamer machen, etwa aus EMV Gründen.
Dazu noch die Flanken etwas runder durch andere Bestückung.
Nur mache ich keine Produkte in dem Sinne, EMV ist zwar wichtig, aber 
normalerweise nicht entscheidend.
Und die Störabstrahlung messen um die Wirksamkeit einzelner Maßnahmen zu 
überprüfen könnte ich eh nicht.

von Rudolph R. (rudolph)


Lesenswert?

Rudolph R. schrieb:
> A little heads up, 5.0 will remove FT80x support.
> But 5.0 will also support BT817/BT818 and since I do not even have a
> programming manual for EVE4 yet, do not hold your breath. :-)

Time for a status update, I just finished annother step of what I had in 
mind for 5.0 and somehow it went a lot smoother than I thought it would.

- FT800 / FT801 support is gone
- split all display-list commands into two functions: EVE_cmd_XXX() and 
EVE_cmd_XXX_burst()
- switched to use REG_CMDB_WRITE

My display-list generation looks like this now:
1
EVE_start_cmd_burst(); /* start writing to the cmd-fifo as one stream of bytes, only sending the address once */
2
EVE_cmd_dl_burst(CMD_DLSTART); /* start the display list */
3
EVE_cmd_dl_burst(DL_CLEAR_RGB | WHITE); /* set the default clear color to white */
4
EVE_cmd_dl_burst(DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG); /* clear the screen - this and the previous prevent artifacts between lists, Attributes are the color, stencil and tag buffers */
5
EVE_cmd_dl_burst(TAG(0));
6
EVE_color_rgb_burst(BLACK);
7
EVE_cmd_text_burst(10,190,29,0, "The quick brown fox...");
8
EVE_cmd_dl_burst(DL_DISPLAY);  /* instruct the graphics processor to show the list */
9
EVE_cmd_dl_burst(CMD_SWAP); /* make this list active */
10
EVE_end_cmd_burst(); /* stop writing to the cmd-fifo */

And to pick one example of what this looks like underneath with V4:
1
void EVE_cmd_bgcolor(uint32_t color)
2
{
3
  EVE_start_cmd(CMD_BGCOLOR);
4
5
  if(cmd_burst)
6
  {
7
    spi_transmit_async((uint8_t)(color));
8
    spi_transmit_async((uint8_t)(color >> 8));
9
    spi_transmit_async((uint8_t)(color >> 16));
10
    spi_transmit_async(0x00);
11
  }
12
  else
13
  {
14
    spi_transmit((uint8_t)(color));
15
    spi_transmit((uint8_t)(color >> 8));
16
    spi_transmit((uint8_t)(color >> 16));
17
    spi_transmit(0x00);
18
    EVE_cs_clear();
19
  }
20
21
  EVE_inc_cmdoffset(4);
22
}

With 5.0 this looks a bit different:
1
void EVE_cmd_bgcolor(uint32_t color)
2
{
3
  if(!cmd_burst)
4
  {
5
    EVE_start_command(CMD_BGCOLOR);
6
    spi_transmit((uint8_t)(color));
7
    spi_transmit((uint8_t)(color >> 8));
8
    spi_transmit((uint8_t)(color >> 16));
9
    spi_transmit(0x00);
10
    EVE_cs_clear();
11
  }
12
}
13
14
void EVE_cmd_bgcolor_burst(uint32_t color)
15
{
16
  spi_transmit_burst(CMD_BGCOLOR);
17
  spi_transmit_burst(color);
18
}

So spi_transmit_burst() replaces spi_transmit_async().
It will either write out four bytes over SPI or add a 32 bit value to 
the DMA buffer instead of splitting the parameters into bytes.

The normal commands are protected to be used outside of command-burst, 
they will just do nothing.
The new _burst commands are not protected anymore and also do not call 
annother function anymore.

I still have to finish this and retest this with a more complex display 
list but the initial speed tests I did back in June showed an 
improvement of about 30%, so display list generation will be faster.

Also the binary size should be a little smaller since all the functions 
that are not needed are removed by the linker.

von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Okay, I just did the first test directly comparing V40 und V50.
Attached are the functions that are compared.
These are functionally the same but for V50 all functions between 
EVE_start_cmd_burst() and EVE_end_cmd_burst() have the new suffix 
"_burst" attached.

This is just the simple test code I am using in the examples.

And the result surprised me a little.

V40
TFT_display() with DMA: 129µs
prog-size: 15436
TFT_display() without DMA: 360µs
prog-size: 15276

V50
TFT_display() with DMA: 51µs
prog-size: 12524
TFT_display() without DMA: 324µs
prog-size: 13420

That is fairly substantial.

The test werde done with an ATSAMC21 running 48MHz and an EVE3-50G.

And as V50 is somewhat tied to BT817/BT818, there was this statement 
over in the BRT Community a couple of days ago:
"The BT817 and BT818 will be released at the beginning of November"

I do already have a BT817 based module to tinker with, I can not share 
any details yet, but I should be prepared for the release. :-)

von Rudolph R. (rudolph)


Lesenswert?

I just did annother small scale test, this time with an Arduino UNO 
clone and a slightly modified version of my example code.

V4:
TFT_display(): 664µs
prog-size: 12272

V5:
TFT_display(): 520µs
prog-size: 10322

So it might be less comfortable to have separate EVE_cmd_xxx() and 
EVE_cmd_xxx_burst() functions, but it sure is faster and takes less 
space even on 8 bit controllers.

And I changed my plans, I will release this earlier.
I only have to remove anything related to BT817 for now before I put it 
up on Github.
Well, I also need to brush up, modify and test my example codes.

von Rudolph R. (rudolph)


Lesenswert?


von Werner (Gast)


Lesenswert?

Hallo Rudolph,
ich arbeite gerade an einem Projekt mit dem FT811 und habe eine einfache 
Frage:
Gibt es eine einfache Möglichkeit zum Zeichen eines gefüllten Dreiecks?
Habe dazu leider nichts gefunden.
Danke im Vorraus.
Werner

von Rudolph (Gast)


Lesenswert?

Nein, Dreiecke kann EVE nicht, zumindest keine gefüllten.
Aber, mit Edgestrip und Scissors kann man das wohl hinbekommen, das 
fällt nur nicht mehr in die Kategorie "einfach".

von Rudolph (Gast)


Lesenswert?

Hier wird sowas in der Art diskustiert, nur probiert habe ich das noch 
nicht: http://www.brtcommunity.com/index.php?topic=163.0

von Werner (Gast)


Lesenswert?

Danke für die schnelle Antwort!
Das schau ich mir mal an.

Werner

von Daniel S. (snipod)


Lesenswert?

Hi,
wollte mich auch mal kurz zu Wort melden.
Ich habe meine ersten Schritte mit dem EVE Controller auf einem ESP32 
mit Rudolphs Bibliothek gemacht und kann nur sagen, sau gut und vielen 
Dank!

Ich habe noch eine Hardware-Spezifische Frage und hoffe, dass mir jemand 
weiterhelfen kann.

Ich würde gerne für mein Projekt ein eigenes HMI erstellen, leider werde 
ich aus den Informationen, die man bei Bridgetec erhält nicht ganz 
schlau.
Und zwar würde ich gerne ein 4" Display mit 720x720 px und CTP verbauen 
und es mit einem EVE4 ansteuern.
Matrix Orbital baut wohl gerade so ein Display, allerdings wollen die 
mir meine Kundenspezifischen Wünsche nicht so ganz erfüllen (SPI über 
LVDS + Spannungsregler on Board...) 
https://www.matrixorbital.com/ftdi-eve/eve-bt817-bt818/eve4x-40g

Das Panel habe ich denke ich gefunden:
https://www.panelook.com/TL040HDS01-TDO-4-inch-4-square-720-720-tft-module-IPS-RGB-interface-touch-optionalw-YY1821-detail_92079.html

Meine Frage wäre: Kann der EVE ohne große Probleme die 720x720 px 
ansteuern (Nominell ja nur 800x600), Funktioniert das mit den "nur" 18 
Bit Farben? Hat jemand den ein oder anderen beispiel-Schaltplan? Bei NHD 
gibts ja bisschen was aber würde mir gerne mehr als nur ein Beispiel mal 
anschauen.

Für alle Tips und Hilfe bin ich sehr dankbar :)

von Rudolph R. (rudolph)


Lesenswert?

die 720x720 sind erstmal so für sich kein Problem, das würde auch mit 
den FT81x gehen.
Wo der BT815 und erst recht der BT817 einen enormen Unterschied machen 
ist in der erreichbaren Wiederholrate.
Der BT815 hat den Vorteil einen höheren Basistakt zu haben und 
entsprechend einen daraus abgeleiteten höheren Pixel-Clock machen zu 
können.
Die BT817 gehen da einen Schritt weiter und sind generell besser geignet 
für Displays mit ein wenig mehr Pixeln, nur wieso, weshalb, warum, kann 
ich nicht ausplaudern. :-)
Aus dem Grund ist auch der ganze BT817/BT818 Code aus der V5 meiner 
Library entfernt.

Weniger Bits pro Farbe gehen schon, die unteren Bits bleiben dann offen 
soweit ich weiß.
Im Datenblatt vom FT81x sieht man das, die FT810/FT811 haben R0, R1, G0, 
G1, B0 und B1 gar nicht erst heraus geführt.
Mir fällt nur gerade kein Modul ein das einen FT812/FT813/BT81x 
verwendet aber nur 6 Bits pro Farbe nutzt.
Ich finde das nur anders herum, ein FT810 oder FT811 und nicht alle 
Anschlüsse am Display belegt.

NHD, also Newhaven ist jetzt auch nicht gerade das schönste Beispiel für 
Informationen so im Allgemeinen.
Auf der Homepage steht das die EVE Module Open Source wären, die Daten 
bekommt man aber nicht mal auf Anfrage, weil die offenbar gar nicht 
wissen wofür das "Source" eigentlich steht.
Immerhin haben die einen Schaltplan im Manual, das machen längst nicht 
alle so.


Ich habe mich damit abgefunden, dass ich einfach nicht die Stückzahlen 
habe um meine Wünsche in ein Display gegossen zu bekommen.

Also baue ich mir Platinen die ich über das Folien-Kabel mit den 
Display-Modulen verbinden kann.
Zwei Varianten davon speziell für 3D-Drucker habe ich veröffentlicht:
https://github.com/RudolphRiedel/EVE_display-adapter

Es gibt aber auch noch D5019-02, D5019-03, D5019-04 und D5019-06. :-)

Die D5019-02 ist eine Briefmarke für die 16pol. Schnittstelle von Glyn, 
der D5019-01 sehr ähnlich, nur ohne den dicken 10pol. Stecker.
Die D5019-03 hat einen SAMC21E18A drauf und eine CAN-FD-Schnittstelle.
Die D5019-04 hat einen SAMC21E18A und 1x CAN-FD und 1x LIN.
Die D5019-06 kann ich mit einem SAMC21J18A oder einem SAME51J19A 
bestücken und 2x CAN-FD und 2x LIN nutzen.

Mein aktuelles Projekt verpackt ein EVE3-43G in eine Art Tablett-Gehäuse 
mit der D5019-06, auf einem SAMC21 läuft die ganze Anwendung, ein CAN 
spricht mit dem Auto und ein LIN läuft als Master für eine weitere 
Komponente.
Mein Projekt davor hatte ein EVE2-70G und eine D5019-04 im Gehäuse und 
auf dem SAMC21 lief nur das HMI, Touch wurde per CAN gemeldet und die 
Anzeige auf Anforderung per CAN aktualisiert.

Bei den kleinen Displays packe ich die Controller-Platine als Sandwich 
über die Display-Platine.
Bei den 7" ist genug Platz das daneben zu legen.

Wenn ich denn unbedingt LVDS oder RS422 oder was anderes passives machen 
müsste was wieder einen SPI umgesetzt wird, würde ich entsprechend eine 
neue Adapter-Platine dafür bauen.
Na okay, eher würde ich versuchen dem Kollegen der das haben will die 
Geschichte auszureden und statt dessen eine Anbindung per CAN und 
Controller anbieten. :-)

von Daniel S. (snipod)


Lesenswert?

Hi Rudolph,
erst mal vielen Dank für die fundierte Antwort!

Offensichtlich bist Du der EVE-Guru :)

Vermarktest Du deine BT816/817 basiertes Wissen, oder hat dein AG da die 
Hand drauf? :)

Der Kollege, der sich das mit dem SPI über LVDS ausgedacht hat, bin 
ich... Die Idee dahinter ist, dass ich mein HMI, welches dezentral von 
meinem Steuergerät verbaut werden wird, über mein Steuergerät updaten 
können will. Wenn ich nun einen weiteren Controller auf der 
Display-Platine verbaue, müsste ich diesen dann über z.B. CAN Updaten. 
Das wäre natürlich möglich, ob es wirklich besser ist, als SPI <-> LVDS 
/ RS422 Konversion weiß ich nicht... die LVDS Treiber / Receiver 
SN65LVDS33 / 31 sind jetzt nicht gerade aufwendig zu implementieren und 
auch nicht wirklich teuer.
CAN hätte den Charm, dass man weniger Kabel bräuchte 4 (5V/GND/CAN H/CAN 
L) vs 12, oder sogar auf eine kabellose Kommunikation ausweichen 
könnte... Außerdem wäre der Controller etwas entlastet, wobei sich mein 
ESP32 mit 240 MHz aktuell doch noch ziemlich langweilt und die 
Programmierung des Hauptprogramms ist so gut wie fertig...

Ich fange einfach mal an, einen Schaltplan zu erstellen und teile meinen 
Progress mit, vielleicht hat ja mal jemand ein Auge drauf ;)

Viele Grüße

von Rudolph (Gast)


Lesenswert?

Daniel S. schrieb:
> Offensichtlich bist Du der EVE-Guru :)

Naja, ich bin eifrig bemüht, aber FTDI/BRT möchte auf viele meiner 
Fragen einfach nicht antworten. :-)

> Vermarktest Du deine BT816/817 basiertes Wissen, oder hat dein AG da die
> Hand drauf? :)

Weder noch, mein AG macht wenig bis keine Produkte, meine Projekte sind 
mehr so interne Tools, Einzelstücke.
Ich sehe das als Hobby und freue mich wenn ich das auch mal im Job 
anwenden kann.

> Der Kollege, der sich das mit dem SPI über LVDS ausgedacht hat, bin
> ich...

Da muss ich Dich enttäuschen, kein Daniel S. in unserem Telefonbuch. :-)

Ich habe ja nur ein wenig aus dem Nähkästchen geplaudert was für mich 
gerade Sinn macht, wir haben überall CAN und die Tools dafür.

Aber die Platinen für die Drucker gehen ja eher in die Richtung was Du 
gerade brauchst, Schnittstelle, Netzteil, kein Controller.
Das ist einfacher umzusetzen und flexibler als eine komplette Platine 
mitsamt EVE drauf zu bauen, vor allem weil sich dann der 
Modul-Hersteller mit den Displays an sich herum ärgern muss.

> Außerdem wäre der Controller etwas entlastet, wobei sich mein
> ESP32 mit 240 MHz aktuell doch noch ziemlich langweilt und die
> Programmierung des Hauptprogramms ist so gut wie fertig...

Was soll der eigentlich grob noch so machen? Die können ja eigentlich 
fast nichts per I/O.

von Daniel S. (snipod)


Lesenswert?

Rudolph schrieb:
> Naja, ich bin eifrig bemüht, aber FTDI/BRT möchte auf viele meiner
> Fragen einfach nicht antworten. :-)

Ja, die sind irgendwie ziemlich langsam...

Rudolph schrieb:
> Ich habe ja nur ein wenig aus dem Nähkästchen geplaudert was für mich
> gerade Sinn macht, wir haben überall CAN und die Tools dafür.

CAN an und für sich ist ja auch nicht wirklich kompliziert, ich habe 
auch schon eine Handvoll Projekte damit gemacht, allerdings wird damit 
der ganze Programmieraufwand noch höher was das Update angeht. Mein 
Problem ist, dass das ganze zu groß wird, wenn ich es als "Rucksack" auf 
so ein EVE Board setze :( Das Projekt soll möglichst schlank werden, 
damit es gut zu verbauen ist, bzw gut in der Hand liegt.
Es handelt sich hier nicht um ein Einzelstück, aber auch nicht um eine 
Großserie, da mach ich mir nichts vor... Es soll am Ende eine Steuerung 
für ein Luftfahrwerk werden. Das heißt der Controller muss ein paar 
Sensoren auslesen und basierend auf deren Daten und den Eingaben des 
Benutzers Ventile öffnen...
"mehr" ist es nicht...
Die IO Kapazitäten des ESP erweitere ich aktuell einfach mit i2c ics, 
das funktioniert soweit auch ganz gut :) Ich habe mich seinerzeit für 
den Esp entschieden, da ich den Support und die Doku ganz gut finde, 
außerdem kann man Updates beliebig einfach einspielen und so weiter... 
Um seine magere IO Ausstattung komme ich ja per i2c ganz gut herum. Am 
Ende brauch ich eh "nur" 12 ADC Kanäle und um die 10 GPIOs...

Rudolph schrieb:
>> Der Kollege, der sich das mit dem SPI über LVDS ausgedacht hat, bin
>> ich...
>
> Da muss ich Dich enttäuschen, kein Daniel S. in unserem Telefonbuch. :-)

Ich meinte natürlich nicht das Prinzip, sondern als "workaround" für 
längere Kabellwege im KFZ in dieser Applikation :)

Ich schau mal wie weit ich komme und poste einfach mal meinen 
Schaltplan... :)

von Rudolph (Gast)


Angehängte Dateien:

Lesenswert?

Daniel S. schrieb:
> Rudolph schrieb:
>> Naja, ich bin eifrig bemüht, aber FTDI/BRT möchte auf viele meiner
>> Fragen einfach nicht antworten. :-)
>
> Ja, die sind irgendwie ziemlich langsam...

Das auch, ich meinte das aber wie ich schrieb, meine Fragen gehen zum 
Teil etwas zu tief. :-)

Daniel S. schrieb:
> Das Projekt soll möglichst schlank werden,
> damit es gut zu verbauen ist, bzw gut in der Hand liegt.

Mit den I/Os ist das schwieriger, keine Frage.

Angehängt mal zwei Bilder mit was ich gerade so herum spiele.
Mit 18mm Dicke ist das recht fett für ein "Tablett", liegt aber gut in 
der Hand.

Wenn man da mehr Kabel raus führen würde, wäre das aber sicher schnell 
sehr lästig, ich muss da aktuell nur +/-/CAN/LIN raus führen und es wird 
auch am Ende nicht mehr in der Hand gehalten.

Ein Platinchen als Schnittstellen-Adapter müsste deutlich kleiner 
werden.

von Daniel S. (snipod)


Angehängte Dateien:

Lesenswert?

Rudolph schrieb:
> Angehängt mal zwei Bilder mit was ich gerade so herum spiele.
> Mit 18mm Dicke ist das recht fett für ein "Tablett", liegt aber gut in
> der Hand.

Sieht sehr robust aus :) Ich denke für den Stationären Einsatz und 
generell als Einzellösung bin ich auch immer ein Freund für solche 
"Zusatzlösungen" um Entwicklungstools herum. Leider wird so etwas meinen 
Ansprüchen an dieses Projekt nicht so ganz gerecht :(

In der Kommunikation mit den Herstellern dieser EVE Boards kam bisher 
eigentlich raus, dass zumindest die Leute die mir die Mails schreiben, 
nicht wirklich wissen worum es geht...

Ich habe mal, basierend auf dem DB des BT815Q, sowie meiner bisherigen 
Testplatine (SPI <-> LVDS) einen Schaltplan erstellt, der relativ 
komplett und vor allem am Ende ziemlich kompakt sein dürfte.

Im DB des Displays, was ich gefunden habe, steht leider nichts zum 
"Reset" Pin, außerdem hab ich noch keine Info, was den Anschluss das CTP 
betrifft...

Den Reset Pin "Active Low" würde ich entweder einfach an 3V3 oder mit an 
PD vom EVE hängen...(?)

Vielleicht finde ich ja noch ein besser dokumentiertes Panel in der 
Größe und Auflösung mit 24 bit RGB... mal schauen

von Rudolph (Gast)


Lesenswert?

Die Belegung von dem 40pol. am Panel sagt mir gleich wieder warum ich 
sowas nicht selber machen will, das passt zu nichts anderem. :-)

Die Positionen der Kabel am Display sind das nächste Problem.
Wenn man zwei Panels mit der gleichen Anschlussbelegung gefunden hat 
kann man sicher sein, dass die Kabel nicht auf der gleichen Position 
sind, oder unterschiedlich lang, das CTP Kabel mehr oder weniger Pins 
hat oder alles zusammen.

Für den Reset könnte es helfen ein Datenblatt von dem verbauten YY1821 
Treiber Chip zu haben, der chinesische Hersteller AXS bietet aber 
erstmal keines zum Download an.

So richtig ungewöhnlich ist das auch nicht, Displays sind keine 
Commodity Items und entsprechend ist das immer wieder lustig wenn man zu 
irgendeinem Display Informationen haben möchte.
Wenn man weniger als 100k Displays kaufen möchte existiert man für die 
Hersteller praktisch nicht.

Daniel S. schrieb:
> außerdem hab ich noch keine Info, was den Anschluss das CTP
> betrifft...

Das dürfte daran liegen, dass das Display gar keinen Touch hat.


Da fehlen wahrscheinlich auch noch ein paar Pullup/Pulldown Widerstände.
Und vielleicht auch noch Reihenwiderstände in den SPI Leitungen, damit 
man bei Problemen was über Null Ohm bestücken könnte.

von Daniel S. (snipod)


Lesenswert?

Rudolph schrieb:
> Da fehlen wahrscheinlich auch noch ein paar Pullup/Pulldown Widerstände.
> Und vielleicht auch noch Reihenwiderstände in den SPI Leitungen, damit
> man bei Problemen was über Null Ohm bestücken könnte.

jaja, ich weiß :) war ja nur der stand ohne das richtige Display und 
so...

Rudolph schrieb:
> Das dürfte daran liegen, dass das Display gar keinen Touch hat.

Das stimmt, gibt es aber auch mit Touch und ist beim Hersteller 
angefragt...


Ich überlege gerade doch einen Controller auf die Platine zu packen und 
CAN zu nutzen... Vorteile wären, dass es 1. weniger Kabel sind, 2. CAN 
sicherlich noch mal Störungsunanfälliger ist als SPI über LVDS und 3. 
ich Displays nutzen könnte, deren Controller zusätzlich über SPI 
konfiguriert werden müssen, ohne noch einen weiteren LVDS Receiver auf 
die Platine packen zu müssen.

Nachteil wäre ich müsste noch Routinen Schreiben, um den Controller am 
Display über CAN upzudaten. Ist natürlich kein riesen Problem, über 
Bluetooth und WiFi habe ich es auch schon implementiert am ESP...

von Ioan Mihai C. (mihaicozac)


Lesenswert?

Hallo nochmal,
  Versuche gerade eine Screenshot Funktion zu schreiben, und wie 
erwartet funktioniert nicht wie es seien sollte. Die Funktion startet 
und läuft, der Bildschirm zeigt bewegende vertikale Streifen die die 
verschiedenen Zeilen des Bildschirminhaltes entsprechen, wenn das Bild 
fertig gescannt wurde springt dann zurück auf normales Bild. Die Daten 
werden über die zweite serielle Anschluss des ESP32 versendet, auf dem 
Computer mit die Software "Free Serial Port Monitor" in .ppm Datei 
gespeichert danach mit Paint.net überarbeitet. Leider bekomme ich auf 
dem Computer nur vertikale Streifen als Dateiinhalt, die noch nicht mal 
einer originale Bildzeile ähnlichen. Die Kopfzeile der Datei ist OK, 
P6.800.480.255 (.ppm header).
Bin mir sicher dass ich irgendwas falsch mache, weiss aber nicht wo und 
was.
Anbei meiner verwendete Code:
1
 void screenshot()
2
 {
3
  unsigned long RAM_BUFFER = 0x00010000; // BUFFER START ADDRESS
4
  unsigned int x, y;
5
  EVE_memWrite8(0x00302010UL,1); // REG_SCREENSHOT_EN ACTIVATED
6
  Serial2.write("P6\n800\n480\n255\n");  // PPM FORMAT HEADER
7
  for (y = 0; y < 480; y++)
8
   {
9
    EVE_memWrite16(0x00302014UL, y);     // REG_SCREENSHOT_Y
10
    EVE_memWrite8(0x00302018UL, 1);      // REG_SCREENSHOT_START
11
    for (x = 0; x < 800; x++)
12
     {
13
      unsigned char b = EVE_memRead8(RAM_BUFFER + x);
14
      unsigned char g = EVE_memRead8(RAM_BUFFER + x + 1);
15
      unsigned char r = EVE_memRead8(RAM_BUFFER + x + 2);
16
      Serial2.write(r);
17
      Serial2.write(g);
18
      Serial2.write(b);
19
     }
20
   }
21
  EVE_memWrite8(0x00302010UL, 0);        // REG_SCREENSHOT_EN DEACTIVATED 
22
 }
Bin für jeden Tipp dankbar.

: Bearbeitet durch User
von Rudolph (Gast)


Lesenswert?

Du hast doch schon einen FT81x, warum nimmst Du dann nicht 
CMD_SNAPSHOT2?

Selber benutzt habe ich das auch noch nicht, vor allem da ich die Daten 
nicht aus der Hardware raus bekomme.
Aber in einem Projekt hat ein Kollege das praktisch so benutzt:

EVE_cmd_snapshot2(EVE_RGB565, SNAPSHOT_BUFFER_START, 
Snapshot_X_Start_ui16, Snapshot_Y_Start_ui16, Snapshot_X_Size_ui16, 
Snapshot_Y_Size_ui16);

Für die V4 meiner Library käme da noch hinzu:
EVE_cmd_execute();

Für die V5 braucht man das aber nicht.

Danach ging das dann über CAN raus und er hat das irgendwie am PC 
eingelesen und konvertiert, war schon schick soweit.

von Ioan Mihai C. (mihaicozac)


Lesenswert?

Danke, werde mal probieren.

von Simon (Gast)


Lesenswert?

Hallo nochmal auch von mir,

für meine Screenshotfunktion verwende ich snapshot2, die Rudolph bereits 
empfohlen hat. Damit gab es bei mir keine Probleme.
Das Prinzip bei mir ist ähnlich, ich schreibe den Screenshot 
streifenweise in eine Datei auf einen USB-Stick. Das kann ich mir dann 
auf dem PC mit ffmpeg in ein gültiges Bild-Format konvertieren.
Was mir spontan auffällt ist, dass die snapshot Funktion, die du 
verwendestest das Bild im ARGB4-Format mit 16 Bit pro Pixel abspeichert. 
Du liest allerdings 24 Bit pro Pixel aus, wodurch sich alles verschieben 
dürfte. Die Zuweisung der RGB-Werte stimmt dann dementsprechend auch 
nicht.

von Rudolph R. (rudolph)


Lesenswert?

It is happening. :-)
https://brtchip.com/bt81x/

Following the official release of BT817 / BT818 with datasheet and 
programming manual I just pushed the first release of my code library to 
Github with support for BT817 / BT818.

https://github.com/RudolphRiedel/FT800-FT813

There may be some kinks left as I did not have the programming manual 
before and was using a preliminary version of the datasheet, but in 
general it works.

von Werner (Gast)


Angehängte Dateien:

Lesenswert?

Hallo Rudolph,

ich bekomme bei einem Display einen Streifen auf einen Button (siehe 
Bild, Button Prog)

Weisst du woran das liegen kann?

Viele Grüsse
Werner

von Karol (Gast)


Lesenswert?

Werner schrieb:
> Hallo Rudolph,
>
> ich bekomme bei einem Display einen Streifen auf einen Button (siehe
> Bild, Button Prog)
>
> Weisst du woran das liegen kann?
>
> Viele Grüsse
> Werner

Are you sure, this line is only on "Prog" button? I saw something like 
this when ZIF connector has some dust on pin/pins (connector was dirty 
inside).

Best's
Karol

von Werner (Gast)


Lesenswert?

I have it on another button with red color, too. And it deoends on the 
color I use.
When I use another display (other manufacturer) there is no line.

von Rudolph R. (rudolph)


Lesenswert?

Okay, das ist mir auch noch nicht untergekommen.

Ist das ein normaler Button oder was eigenes?
Was ist das überhaupt für ein Display? CFAF240400?

Kannst Du die GUI soweit frei schneiden das Du einen Testcase erstellen 
kannst ohne sonst was von dem Projekt weitergeben zu müssen?

Oder zeigt doch mal bitte wie die Zeilen für den Button und unmittelbar 
drum herum so aussehen.

von Wertner (Gast)


Angehängte Dateien:

Lesenswert?

Es ist ein Button, der mit dem Button Befehl erstellt wird.

Hier der Code Ausschnitt:

EVE_cmd_romfont(0,32);      // Romfont laden
EVE_cmd_dl(DL_COLOR_RGB | WHITE);
EVE_cmd_fgcolor(PINK_1);
EVE_cmd_dl(TAG(t_prog));
EVE_cmd_button(250, 710, 220, 80, 0, 0, "    Prog");
EVE_cmd_dl(DL_COLOR_RGB | WHITE);
EVE_cmd_setbitmap(MEM_PIC_progsym, EVE_ARGB2, 50, 50);  // Prog Symbol 
Taste
EVE_cmd_dl(DL_BEGIN | EVE_BITMAPS);
EVE_cmd_dl(VERTEX2F(267, 725));

Farben:
#define PINK_1  0xB97894UL
#define WHITE  0xffffffUL
#define RED  0xDC3545UL

Bei einem Button der Farbe RED gibts auch einen Streifen.
Wenn ich die Farben ändere bekomme ich die Streifen (fast ganz) weg.

Das Display ist von Autronic, speziell für dieses Projekt, Datenblatt im 
Anhang. Möglicherweise sollte ich mir die Timings mal genauer ansehen.

Wenn ich das Display vom VM810C Kit nehme ist kein Streifen zu sehen.

von Rudolph R. (rudolph)


Lesenswert?

Das sieht soweit doch erstmal harmlos aus.
FT813?
Was der Button mit dem Bild zu tun hat ist mir so erstmal nicht klar.

Das Timing von dem Panel ist etwas anders als bei allen anderen 800x480 
die mir bisher untergekommen sind.
Das ist reichlich straff mit kurzen Zeilen und kaum extra Zeilen.
Meine "Standard" Timings für 800x480 würde ich dafür auch nicht 
verwenden wollen.

von Werner (Gast)


Lesenswert?

Hallo Rudolph,
Der Controller ist der FT811.
Das Bild sind die 4 Quadrate auf dem Button. Das Timing schau ich mir 
jetz
mal noch genauer an aber trotzdem vielen Dank für die Unterstützung!!

von Rudolph R. (rudolph)


Lesenswert?

Äh, ja, jetzt, danke. :-)

>Der Controller ist der FT811.

Lohnt sich das wirklich?
In der Apotheke kostet der FT813 doch gerade mal 30 Cent mehr pro Stück 
bei 100 Stück, aber dafür kann der das Display auch mit 24 Bit Farbe 
ansteuern.

Klar, das sollte nichts machen, aber so ein schönes Display und dann die 
Farbtiefe durch den EVE Chip beschneiden... :-)

Ich glaube ich muss das mal ausprobieren.
Eigentlich sollte das funktionieren, aber zuweilen führen "komplexe" 
GUIs auch zu interessanen Problemen für EVE. :-)

von Ioan Mihai C. (mihaicozac)


Lesenswert?

#define PINK_1  0xB97894UL

Bei 6 bit pro Farbe sind keine ungerade Werte möglich...
Vielleicht ist der Wert B9 für Rot nicht zugelassen für FT811.

von Ioan Mihai C. (mihaicozac)


Lesenswert?

Also wie 00, 03, 07, 0A usw. als Werte.

von Werner (Gast)


Lesenswert?

Das mit den ungeraden Werten macht keinen Sinn, da ein anderes Display 
ja ohne den Streifen funktioniert.
#Rudolph
Mit der 24Bit Farbtiete hast du schon recht, ich war bisher auch der 
Meinung, daß der Preisunterschied grösser ist... und man darf auch nicht 
vergessen, daß man sich immer noch Platz nach oben lassen muß :-)

von Rudolph R. (rudolph)


Lesenswert?

Der FT811 verarbeitet die Farbe schon, nur bei der Ausgabe werden die 
unteren zwei Bits nicht ausgegeben, dafür hat der schlicht die Pins 
nicht.

Nach Oben ist dann doch noch Luft, die BT817 sind ja gerade erst 
offiziell released. :-)

von roter_Milan (Gast)


Lesenswert?

Moin zusammen,

erstmal Danke an rudolph für deine Library, die macht vieles einfacher!

Ich hab dein Bsp. aus github nachgebaut und dies hat auch funktioniert. 
Allerdings nicht immer nach einem Neustart. Dann fehlten Teile der 
statischen display list oder die Bilder wurden nicht richtig fertig 
geladen. Wenn ich aus deinem Bsp. "EVE_cmd_append_burst(MEM_DL_STATIC, 
num_dl_static)" auskommentiert hatte funktionierte aber zumindest der 
dynamische Teil immer nach einem Neustart.

Nach einigen Stunden habe ich dann herausgefunden, dass mein Timer (5ms) 
anscheinend die Übertragung der statischen display list unterbrochen 
haben muss.
In dem Timer werden "tft_touch()" (alle 5ms) und "tft_handling()" (alle 
25ms) aufgerufen.

Die Lösung des ganzen war dann die Timer erst nach dem tft_init() zu 
initialisieren. Seit dem funktioniert es wie es soll :)

Ich schreib das nur, falls jmd auch mal dieses Problem hat. So muss er 
nicht so viele Stunden investieren wie ich. Vllt. ist es ja auch normal 
die timer als letztes zu initialisieren...

P.S. Ich benutze momentan einen SAME54P20A mit dem EVE3-50G-BLM.

Gruß

von Rudolph R. (rudolph)


Lesenswert?

Ich würde tft_touch() und tft_handling() nicht per Interrupt machen.
Selbst tft_touch() dauert doch dafür viel zu lange und das 
tft_handling() sowieso.

Klar, der "Scheduler" aus meinen Beispielen ist sehr stumpf mit der 
Hauptschleife die per Systick Timer alle 5ms durchlaufen wird.
Aber im Grunde genommen sieht das in einem größeren Projekt auch nicht 
anders aus, da ist dann nur weniger Code direkt in der main.c, etwa so:
1
while (1) 
2
{
3
 if(system_tick)
4
 {
5
  system_tick = 0;
6
7
  watchdog_task();
8
  debug_led_task();
9
  can_task();
10
  display_task();
11
  can_task();
12
 }
13
}

Nein, das habe ich so jetzt auch noch nirgendwo, außer die Anforderung 
den Code per Unit-Testing testen zu wollen, fällt mir dafür auch kein 
vernünftiger Grund ein.

Was da fehlt ist eigentlich nur den Controller am Ende schlafen zu 
schicken.
Nur ist das witzlos in Kombination mit dem Display.

Und natürlich findet die Initialisierung da drüber statt. :-)

von roter_Milan (Gast)


Lesenswert?

Das ist mit dem "Scheduler" ist auch eine gute Idee, obwohl die beiden 
Funktionen "tft_touch()" und "tft_handling()" jetzt noch nicht so lange 
brauchen. Werde es bei Gelegenheit mal umbauen.

Das die Initialisierung darüber stattfindet war mir auch klar ;-) bloß 
habe ich halt in der Initialisierung zuerst die Timer initialisiert und 
gestartet und dann das Display initialisiert. Man sollte den Timer eben 
am Ende der Initialisierung starten :-)

von Rudolph (Gast)


Lesenswert?

Das tft_touch() braucht auch auf dem SAME54 mehrere µs für single-touch, 
bei Multi-Touch entsprechend nach Anzahl der ausgewerteten Punkte 
länger.
Das erzeugt eben SPI Traffic.

Und für die Anzeige selber braucht man schon mal ein paar hundert Bytes 
bis mehrere KB.
Selbst wenn die Daten per DMA verschickt werden, den Puffer zu füllen 
kostet auch Zeit.
Das ist alles ein Witz im Vergleich zum Setzen einzelner Pixel, aber 
eben erheblich mehr Zeit als ich einen Controller im Interrupt 
verbringen lassen würde.

Interrupts nutze ich möglichst zurückhaltend um sie als Resource zur 
Verfügung zu haben wenn es wirklich mal darauf ankommt.

Und der Systick-Timer in den ARMs ist genau für sowas gedacht, als 
Zeitbasis für periodisch aufgerufene "Tasks".

von Simon (Gast)


Lesenswert?

Have you used Bridgetek VM816C50A board? I don't see this board in your 
defines in EVE_config.h file.

von Rudolph (Gast)


Lesenswert?

I have not, I tend to avoid resistive touch modules.
But I can look into adding a profile for the 5" display they used.
There is a good chance that the profile for EVE3-50 (EVE_EVE3_50) does 
work for the VM816C50A.

von Rudolph R. (rudolph)


Lesenswert?

I just pushed a small update for EVE_config.h:
- moved the profile for the RiTFT50 over to the one for the RiTFT70
- added a profile for the VM816C50A-D from Bridgetek
- added a profile for PH800480T024-IFC03 and PH800480T013-IFC05 from 
PowerTip

von roter_Milan (Gast)


Lesenswert?

Moin,

habe meinen Code mal nach deinem Vorschlag umgebaut und er läuft soweit 
auch.
Allerdings friert das Display ab und zu ein oder wird komplett schwarz.
Der uC funktioniert allerdings noch, ebenso werden über SPI noch Daten 
gesendet.
Danach kann es erst nach einem Reset wieder genutzt werden.
Ist das Problem irgendwie bekannt?

Danke und Gruß

von Rudolph (Gast)


Lesenswert?

Ich sag mal so, normal ist das nicht, wenn ich mit dem SAME51 sowas 
schon bemerkt hätte, dann wäre das jetzt nicht mehr so. :-)
Also so grundsätzlich, mit nichts anderem auf dem Controller.

Läuft das hier denn durch?
https://github.com/RudolphRiedel/FT800-FT813/tree/5.x/example_projects/EVE_Test_SAME51_EVE3-43G

Also nach "leichter" Umkonfiguration auf die Takt-Quelle, die passende 
SERCOM, den anderen Pins und dem Display?

Kommt sich da was in die Quere?
Soll vielleicht was anderes den gleichen DMA Kanal benutzen?

Ein häufigeres Problem ist auch eine nicht ganz so stabile 
Stromversorgung für das Display.

von roter_Milan (Gast)


Lesenswert?

Habe mir schon fast gedacht, dass du das Problem ansonsten schon gelöst 
hättest :D Ich wollte aber zumindest mal fragen :)

Hab das Problem auch schon gelöst.
Hatte mir die SPI Signale nochmal mit dem Oszi angeschaut und dann 
bemerkt, dass die Jumper Kabel, die ich benutze, nicht die Besten sind.

Nachdem ich zwei Kabel getauscht habe, läuft das Display jetzt auch ohne 
Aussetzer :)

von Rudolph R. (rudolph)


Lesenswert?

Hör bloß auf mit Jumper-Kabeln, bei den letzten die ich gekauft habe 
konnte ich nur gerade so die Leitungen verwenden um da KFZ-Kontakte 
drauf zu crimpen.

von roter_Milan (Gast)


Lesenswert?

Hatte dahingehend noch nie Probleme mit Jumper Kabeln gehabt.
Habe diese aber neugekauft und die Buchsen scheinen nicht so gut zu 
klemmen -.-

Naja wenigstens funktioniert es jetzt :)

von Daniel S. (snipod)


Lesenswert?

Hi Rudolph,
ich habe deine Lib ja schon erfolgreich mit dem ESP32 und dem Arduino 
Framework ausprobiert und finde sie klasse :)

Da ich mit der Funktion des Arduino-Frameworks für den ESP aber nicht 
zufrieden bin, bin ich auf das IDF umgestiegen. Das IDF ist das vom 
Hersteller bereitgestellte Entwicklungsframework für die ESP Serie.

Ich Arbeite gerade daran, deine Software mit dem IDF zum Laufen zu 
bekommen, sehe aber ein paar Probleme, da SPI doch ziemlich anders 
aufgebaut ist, als bei Arduino.

Hast Du Interesse daran, deine Bibliothek um den Support zu erweitern, 
bzw. würdest Du mich dabei unterstützen?

Viele Grüße :)

von Rudolph R. (rudolph)


Lesenswert?

Ich bin ja ohnehin gerade mit den ESP32 und auch ESP8266 am spielen, 
wenn jetzt auch nicht weil ich die selber für irgendwas einsetzen wollen 
würde.
Und eine Sache die ich noch auf dem Zettel habe ist der Arduino-ESP32 
Seite DMA zu verpassen über das IDF was da als driver_lib.a oder so noch 
mit verfügbar ist.

Das wäre zumindest vom IDF her die Richtung, zumindest hoffentlich, wenn 
denn das der gleiche Code ist.
Wie man mit dem ESP32 grundsätzlich klar kommt, so ohne Arduino auf 
RTOS, keine Idee.
Ich würde das auf jeden Fall mit PlatformIO anfangen wollen.

Meine Versuche mit dem ESP8266 haben auch erstmal dazu geführt das meine 
Adapter-Platine und wahrscheinlich auch der ESP8266 gestorben sind, 
Ersatz liegt hier jetzt, nur so richtig motiviert bin ich gerade nicht 
das wieder anzuschliessen. :-)

von Daniel S. (snipod)


Lesenswert?

In das RTOS usw habe ich mich mittlerweile ganz gut eingearbeitet.
Ich werde versuchen deine Lib um die Funktionen zu erweitern damit sie 
auch mit der IDF funktioniert. Meine Erfolge - wenn es welche gibt :) - 
teile ich dann gerne

von Rudolph R. (rudolph)


Lesenswert?

Das erfordert ja nur ein neues Segment in EVE_target.h und EVE_target.c.

Ich scheitere gerade spontan daran ein leeres ESP-IDF in PlatformIO 
anzulegen, das will nur mit Arduino, dabei sollte es auch anders gehen.

von Daniel S. (snipod)


Lesenswert?

Rudolph R. schrieb:
> Das erfordert ja nur ein neues Segment in EVE_target.h und EVE_target.c.
>
> Ich scheitere gerade spontan daran ein leeres ESP-IDF in PlatformIO
> anzulegen, das will nur mit Arduino, dabei sollte es auch anders gehen.

Das ist mir schon klar, nur ich habe es gestern nicht hin bekommen :)
Ich werde mich heute noch mal intensiver damit auseinandersetzen.

In PlatformIO musst Du eigentlich nur Espressif IOT Development 
Framework als Framework auswählen beim erstellen des Projekts... Oder:
platform = espressif32
board = esp32dev (bzw. dein Board...)
framework = espidf

Grüße

von Rudolph (Gast)


Lesenswert?

Naja, eigentlich und so, ich habe gestern über zwei Stunden gebraucht 
bis ich endlich mal espidf-blink compilieren konnte.
Seltsame Fehlermeldungen und keine Lösung dafür, so richtig sauber tickt 
PlatformIO oder auch Espressif-ESP32 noch nicht ganz.
Nach mehrmals Teile in PlatformIO entfernen und neu installieren wollte 
dann cmake nicht.
Am Ende habe ich \.platformio\packages\tool-cmake gelöscht, PlatformIO 
hat es neu installiert und ich konnte compilieren.
Heftig war dann allerdings was da alles für das einfache Blink-Beispiel 
compiliert wird, wie ewig das initial dauert und das da ein 145kB Binary 
bei raus kommt.

Danach hatte ich erstmal genug von dem Mist.

von Daniel S. (snipod)


Angehängte Dateien:

Lesenswert?

Ich habe die Kommunikation soweit am laufen, kämpfe jetzt bisschen mit 
dem Gerät...
Ich komme bei EVE_init() beim initialisieren des Touch Controllers 
niucht aus dem while(eve_busy()) nicht raus.

Aber hier wäre schon mal ein (von SPI Seite her) funktionierendes 
Projekt.

PS: Ich musste spi_write_eeprom in eve_spi_write_eeprom umbenennen, da 
es die Funktion im Framework schon gibt...

EDIT:
EVE_Init läuft durch, Backlight geht auch, nur sehen tu ich nix :(

: Bearbeitet durch User
von Rudolph R. (rudolph)


Angehängte Dateien:

Lesenswert?

Also ich kann schon mal compilieren so ohne Warnungen.
Und von der Struktur her sieht das erstmal so aus wie ich das auch 
gemacht hätte, so weitgehend.
Mal davon ab das ich inhaltlich mit dem ESP32 code noch nicht viel 
anfangen kann.

Nur bleibt das Bild bei mir noch komplett schwarz, nicht mal diese 
einfache Display-Liste wird angezeigt:
1
EVE_cmd_dl(CMD_DLSTART);
2
EVE_cmd_dl(DL_CLEAR_RGB | WHITE);
3
EVE_cmd_dl(DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG);
4
EVE_cmd_dl(TAG(0));
5
EVE_cmd_dl(DL_COLOR_RGB | BLACK);
6
EVE_cmd_text(100,100,28,0,"Hello");
7
EVE_cmd_dl(DL_DISPLAY);
8
EVE_cmd_dl(CMD_SWAP);

Mal den Logic-Analyzer anwerfen, mit der Arduino Seite läuft das.

So ganz das gleiche wie auf der Arduino Seite macht die ESP-IDF Version 
aber noch nicht.

: Bearbeitet durch User
von Daniel S. (snipod)


Lesenswert?

hmmm, das stimmt, das sieht etwas komisch aus...

Haben wir vielleicht ein Problem mit Little / Big Endian oder so?

Bin leider nicht wirklich der SPI Profi, geschweige denn EVE :P

Ich habe im Bridgetek Forum eine Lib gefunden für den ESP32, aber 
funktionieren tut die auch nicht :)
http://www.brtcommunity.com/index.php?topic=100.0

Das Initialisieren EVE_init() läuft bei mir aber durch - ich hab lauter 
Log einträger reingeballert, da ich keinen Logic analyzer besitze...
Nur wie du schon sagst, beim erstellen der DL gibt es dann wohl 
Probleme.

Vielleicht ist es dann tatsächlich dann Little / Big Endian Problem, 
weil beim Initialisieren ist glaube alles noch 8 bit groß, erst später 
kommen dann 16 und 32 bit commands und register

von Rudolph R. (rudolph)



Lesenswert?

Es läuft jetzt bei mir.

Das Problem war die Byte-Order für die 32 Bit Transfers.
Irgendwo muss das doppelt gedreht sein.
Vielleicht ist aber auch auf der Arduino-Seite ein Byte-Dreher drin den 
ich durch das eigene Drehen kompensiert habe.
1
static inline void spi_transmit_32(uint32_t data)
2
{
3
//ESP is little endian
4
//uint32_t be_data = htobe32(data);
5
uint32_t be_data = data;

Und warum das auf dem SPI erstmal so komisch aussieht ist auch 
erklärbar.
Der ESP-IDF Code ist im Moment noch elendig langsam.
So richtig übel langsam.

Ich habe das in der Tabelle nebeneinander gestellt, der Arduino macht 
mehr Traffic, weil der Code da einfach schneller läuft, das heißt der 
BT815 den ich hier ansteuere ist in den Warteschleifen beim Init einfach 
noch nicht fertig und beim langsameren Code in der ESP-IDF Version 
schon.

Dabei ich auch schon die EVE_commands.c gegen die originale ersetzt, so 
ohne die "ESD_LOGE(..." Aufrufe.
Und mit den 40ms Delay am Anfang die Du durch 300ms ersetzt hast.
Das Delay vom ESP-IDF haut übrigens auch nicht hin, das ist zu lang.
Ist jetzt kein Problem, aber auch dadurch sind die Daten auf dem SPI 
beim Init auf den ersten Blick nicht gleich.

Nach den ganzen Erfahrungen, die Code-Qualität von Espressif überzeugt 
mich nicht.
Zwischen zwei Datenbytes auf dem SPI derart lange Pausen einzubauen ist 
schon ein Kunststück, vor allem bei 240MHz Core-Takt.

von Daniel S. (snipod)


Angehängte Dateien:

Lesenswert?

Ich hab das example jetzt auch am laufen... und er braucht zum builden 
der DL ganze 60ms, das ist natürlich nichts.

Ich habe versucht das ganze zu queuen, das wird aber net viel besser... 
Ich habe die delays aber gefixt, dazu muss man nur die tick rate vom 
Scheduler erhöhen, das sollte jetzt besser passen.

Ich habe versucht vom Software Treiber, auf den HAL Treiber umzustellen, 
jetzt zeigt er aber wieder nix an -.-'

Vielleicht kommst Du ja damit weiter :)

von Rudolph (Gast)


Lesenswert?

Naja, inzwischen wundere ich mich nicht mehr über so Sprüche das 
Software-SPI mit dem ESP32 schneller ist als Hardware-SPI.
Das liegt im wesentlichen an der Software die Espressif liefert und der 
Dokumentation dazu.

Hier kann man den Weg für den Arduino Teil nachlesen:
https://github.com/RudolphRiedel/FT800-FT813/issues/14

Zwischen zwei Transfers über 6µs Pausen zu haben ist schon heftig, das 
sind bei 240MHz ja über 1400 Takt-Zyklen.

Um am Ende auf 140µs für die Demo zu kommen habe ich den DMA Support in 
meiner Library genutzt, nur bisher ohne DMA, da der ESP32 Arduino Core 
DMA nicht direkt unterstützt.

Ich bin sicher da geht noch was.

von Rudolph R. (rudolph)


Lesenswert?

Der HAL Treiber ist doch der aus dem Arduino-ESP32?

Das ist jetzt nicht so die beste Idee, im Gegensatz zum ESP-IDF 
unterstützt der nämlich DMA gar nicht.

Ich habe gerade die Pin-Konfiguration an mein Board angepasst und das 
Display umgestellt, jetzt passiert auf dem SPI aber praktisch nichts 
mehr.
SCK macht irgendwas, das ist aber auch alles.

von Daniel S. (snipod)


Angehängte Dateien:

Lesenswert?

hmm...
also ich habe mir jetzt mal einen logic analyzer zugelegt und werde die 
Tage mal schauen wie ich es beschleunigt bekomme.

Bis dahin muss ich erst mal auf Arduino Basis mein Sample Display zum 
Laufen bekommen, da passt aber was noch nicht so 100%-ig.
Ich habe die Timings im Verdacht... Könnte Die sich mal jemand 
anschauen? Ich habe schon bisschen rumprobiert, aber so wirklich 
verstanden hab ich es nicht...

So gehe ich aktuell vor:
1
#define EVE_PCLK  (2L) //PCLK 36 MHz
2
#define EVE_PCLKPOL  (0L) // 0 = Output on Negative Edge, 1 = Output on Positive Edge
3
#define EVE_SWIZZLE  (0L) // dont switch output pins
4
#define EVE_CSPREAD  (0L) // 0 = change r/g/b before clock, 1 = change r/g/b with clock  
5
6
#define EVE_HSIZE  (800L)  /* Thd Length of visible part of line (in PCLKs) - display width */
7
#define EVE_VSIZE  (480L)  /* Tvd Number of visible lines (in lines) - display height */
8
9
#define EVE_VSYNC0  (4L)  /* Tvf Vertical Front Porch */
10
#define EVE_VSYNC1  (8L)  /* Tvf + Tvp Vertical Front Porch plus Vsync Pulse width */
11
#define EVE_VOFFSET  (20L)  /* Tvf + Tvp + Tvb Number of non-visible lines (in lines) */
12
#define EVE_VCYCLE  (824)  /* Tv Total number of lines (visible and non-visible) (in lines) */
13
#define EVE_HSYNC0  (4L)   /* (40L)  // Thf Horizontal Front Porch */
14
#define EVE_HSYNC1  (8L)  /* Thf + Thp Horizontal Front Porch plus Hsync Pulse width */
15
#define EVE_HOFFSET  (20L)  /* Thf + Thp + Thb Length of non-visible part of line (in PCLK cycles) */
16
#define EVE_HCYCLE   (504L)  /* Th Total length of line (visible and non-visible) (in PCLKs) */

Ich versuche eine minimal DL darzustellen:
1
EVE_init();
2
EVE_memWrite8(REG_PWM_DUTY, 0x80);
3
EVE_init_flash();
4
5
EVE_cmd_dl(CMD_DLSTART);
6
EVE_cmd_dl(DL_CLEAR_RGB | WHITE);
7
EVE_cmd_dl(DL_CLEAR | CLR_COL | CLR_STN | CLR_TAG);
8
EVE_cmd_dl(TAG(0));
9
EVE_cmd_dl(DL_COLOR_RGB | BLACK);
10
EVE_cmd_text(100,100,28,0,"Hello");
11
EVE_cmd_dl(DL_DISPLAY);
12
EVE_cmd_dl(CMD_SWAP);

Der Bildschirm bleibt aber weitesgehend weiß :)

von Rudolph (Gast)


Lesenswert?

Solche Timing Parameter sind genau der Grund warum ich nackte TFTs 
ziemlich unlustig finde. :-)

Die meisten 800x480 kommen allerdings mit den Parametern klar die ich in 
EVE_config.h unter "Resolution_800x480" abgelegt habe.
Das habe ich nicht so angelegt weil ich die Datei kleiner bekommen 
wollte, das hat sich aus den ganzen Daten für diverse Displays so 
ergeben.

Das BT815 5" von Riverdi zum Beispiel hatte mit den Daten einen Offset, 
obwohl das in deren Datenblatt so drin steht, grundsätzlich hat das aber 
was angezeigt und mit den Daten aus deren Demo-Software läuft es jetzt 
auch richtig.

Ich habe noch ein Display von Powertip herum liegen, 7" 800x480 FT813.
Das Datenblatt dazu ist praktisch nicht zu bekommen, nur auf Umwegen und 
veraltet, die Daten da drin sind ein Witz und auf Anfragen zu reagieren 
ist Powertip anscheinend zu lästig.

von Daniel S. (snipod)


Lesenswert?

Ich bin in stetem Kontakt mit meinem Lieferanten, der ist auch relativ 
engagiert... leider hat der keine Ahnung vom EVE.

Ich hätte liebend gerne ein "fertiges" Modul genommen, leider habe ich 
immer noch nichts gefunden, was meinen Anforderungen entspricht :( Und 
der Wille zu Kundenspezifischen Lösungen scheint bei den üblichen 
verdächtigen nicht so wirklich gegeben zu sein...

Ich schau mal wie weit ich komme, ich werde berichten :)

Viele Grüße

von Rudolph R. (rudolph)


Lesenswert?

Für die Timing-Parameter braucht der Display-Lieferant auch erstmal 
keine Ahnung von EVE zu haben, aber die Parameter da oben sind schon 
sehr dünn.
Wenn das stimmt müsste das Panel mit einem extrem weiten Bereich an 
Parametern klar kommen.

Was passiert denn mit den "Standard" Parametern?

Hast Du mal 
https://github.com/RudolphRiedel/FT800-FT813/tree/5.x/example_projects/EVE_Test_Arduino_PlatformIO 
ausprobiert?

Trag als Display doch zum Beispiel mal EVE_NHD_50 ein.


Kundenspezisch geht schon, das ist nur eine Frage der Menge.

TFTs sind einfach keine Massenware, das Zeug das für wenig Geld 
verscherbelt wird sind so aufgekauften Restposten für die man erst recht 
keine Daten erwarten kann.

Wenn ich wirklich mit Mengen um mich werfen wollen würde, dann würde ich 
bei Riverdi anfragen.
Vielleicht auch bei Glyn.
Also zumindest wenn ich in Europa bleiben wollen würde.

von Rudolph R. (rudolph)


Lesenswert?

Ach ja, der ESP8266 läuft jetzt auch, oder wieder.
Ich habe die Stelle gefunden an sich der ESP8266 immer wieder resettet 
hat, ich habe einen 32-bit Pointer auf den String für z.B. Buttons und 
Text erzeugt um gleich vier Bytes auf einmal zu kopieren.
Das gab sonst nirgendwo Probleme, auch nicht mit dem ESP32.
Nur kann der ESP8266 nicht per 32 Bit Pointer auf Daten zugreifen die 
nicht 32 Bit ausgerichtet sind.
ARMs können das wohl auch nicht, nur ist das vermutlich nicht 
aufgefallen weil der Compiler dafür gesorgt hat, dass die Strings auf 32 
Bit ausgerichtet sind.

Nun ja, um da nicht noch mal mit einem anderen Controller drüber zu 
stolpern habe ich gleich die ganze Funktion neu geschrieben.

von Daniel S. (snipod)


Angehängte Dateien:

Lesenswert?

Moin,
ich hab mein Problem gefunden. (und es macht für mich keinen Sinn...)

Folgendes: Beim Setup des ILI9806E habe ich ein Kommando hinzugefügt, 
welches das Interface auf 24 RGB festlegt (0x70), jetzt funktioniert es 
einwandfrei. Etwas Tweaking was die Timings angeht und schon hat das 
Display funktioniert.

Warum ich es nicht verstehe? 0x70 ist laut DB der verdammte Default Wert 
dieses Registers!

Jetzt kann ich mich darum kümmern, die Kommunikation mit dem EVE zu 
beschleunigen.

Falls jemand bei irgendeiner Web-Suche hierauf stößt: angehängt der Code 
für die Kommunikation zum ILI9806E über den SPI Treiber der ESP-IDF ;)

PS: mit den "standard parametern" läuft es sogar auch...

von Werner (Gast)


Angehängte Dateien:

Lesenswert?

Hallo zusammen,

kann mir jemand sagen woran es liegt, wenn man so "Störungen" wie im 
Bild auf dem Display bekommt.
Der Controler ist der FT811.

von Rudolph R. (rudolph)


Lesenswert?

Daniel S. schrieb:
> Folgendes: Beim Setup des ILI9806E habe ich ein Kommando hinzugefügt,
> welches das Interface auf 24 RGB festlegt (0x70), jetzt funktioniert es
> einwandfrei.

Schön das es funktioniert, aber das ist ja eklig, die Notwendigkeit den 
eigentlichen Display-Chip zu konfigurieren hatte ich bisher nicht. :-)
Das der ILI9806E ein 9-Bit SPI Interface hat macht das auch nicht 
hübscher.

Das ESP32 Board habe ich immer noch auf dem Tisch liegen mit dem Display 
da dran, die letzten Tage konnte ich mich nur nicht dazu aufraffen mich 
da mal endlich richtig dran zu machen das schneller zu bekommen, auch 
auf der Arduino Seite.


Werner schrieb:
> kann mir jemand sagen woran es liegt, wenn man so "Störungen" wie im
> Bild auf dem Display bekommt.
> Der Controler ist der FT811.

Sowas in der Form habe ich leider auch noch nie beobachtet.
Ist das statisch, oder zappelt das?
Das sieht irgendwie aus wie ein Problem zwischen FT811 und Display.
Was passiert wenn Du den Wert für PCLK mal erhöhst, also den Takt 
verringerst?

Kannst Du das vielleicht frei schneiden und ein minimales Beispiel mit 
einer generischen Display-Liste erzeugen welche das Problem hat?

von Werner (Gast)


Lesenswert?

Hallo Rudolph,
schon doof, daß das nur bei mir passiert.
Das ganze ist nicht statisch, es zappelt ein wenig.

Das mit dem freischneiden ist nicht ganz einfach, da es nur auftritt, 
wenn ich viel in die Liste schreibe.
Im Beispiel wird eine Liste mit bis zu 10 Einträgen angelegt. Diese wird 
dann entsprechend verschoben. Meist fängt es an zu zappeln, wenn mehr 
wie 6 Eintäge drinn sind.

Wenn ich den PCLK erhöhe flackert alles.

Ich versuch mal ein Beispiel freizuschneiden, das dauert allerdings ein 
wenig.

von Rudolph R. (rudolph)


Lesenswert?

Wie voll ist die Display-Liste? Das sieht eigentlich noch total harmlos 
aus.

Und wie oft machst Du den Refresh?
Probiers mal ein wenig langsamer.

von Werner (Gast)


Lesenswert?

Hallo Rudolph,
langsamer bringt leider keine Unterschied.
ich mache alle 20ms einen Refresh.

von Johannes (Gast)


Lesenswert?

Hallo Rudolph!

Ich habe deine Library erfolgreich auf M328 und M644 genutzt. Jweils mit 
NHD43-Displays. Bisher mit einigen simplen Screens und Buttons. Also 
nichts extravagantes. Dennoch: Es klappt super und deine Bibliothek ist 
wikrlich hervorragend. Mein Kompliment!

Als nächstes gibt es ein Projekt mit einem XMEGA64, also mit durchaus 
etwas mehr Performance. Ich möchte eine SD-Karte als Speicher für Bilder 
verwenden um die Screens und die Menüpunkte etwas "schöner" zu 
gestalten. Ähnlich wie das Beispiel App-Mainmenu von FTDI.

Hast du bereits Dateien von SD-Karten eingebunden? Gibt es dazu irgendwo 
Beispielcode, von dem man vorhandene Elemente übernehmen könnte?

Gruß,
Johannes

von Rudolph R. (rudolph)


Lesenswert?

Moin,

Johannes schrieb:
> Hast du bereits Dateien von SD-Karten eingebunden?

Nein, habe ich nicht, als ich noch mit AVR unterwegs war habe ich 
90CAN128 verwendet, dann ATSAMC21 mit 256k FLASH und aktuell habe ich 
ein Projekt laufen mit einem ATSAME51J19A der 512k FLASH hat.
Und dann hat das RiTFT50 das hier gerade vor mir liegt 16MB eigenen 
Speicher und kann ASTC komprimierte Bilder direkt daraus anzeigen.

Die XMEGA habe ich auch nie verwendet, zum einen gibt es die nicht mit 
CAN, zum anderen waren die Includes so anders das ich mich da ohne 
besonderen Grund nie einarbeiten mochte.
Auf der Arbeit habe ich noch ein Eval-Board von einem Seminar rum 
liegen.

Also ich würde durchaus von den XMEGA abraten und einen ATSAMC20 oder so 
empfehlen, also zumindest wenn mich jemand fragen sollte ob er von den 
AVR auf die XMEGA umsteigen soll.
Die Hürde ist in etwa die gleiche, nur sind die ATSAM weniger tot.


Da Speicher der limitierende Faktor ist und praktisch sämtliche Medien 
Block-orientiert arbeiten liest man Dateien in Häppchen ein, so 512 
Bytes oder so.

Für bereits konvertierte Daten habe ich die Funktion 
EVE_memWrite_sram_buffer() eingebaut.
sd_open_file()
wiederhole_bis_ende_der_datei
{
 sd_read_block()
 EVE_memWrite_sram_buffer(ziel+(anzahl*blocklänge), gelesene länge)
}

Die Funktionen EVE_cmd_inflate() und EVE_cmd_loadimage() gehen davon 
aus, dass sich die Daten im Speicher des Controllers befinden, zumindest 
für AVR Controller.
Das kommt von der Harvard-Architektur der AVR Controller und so steht in 
der EVE_target.h für AVR die Funktion fetch_flash_byte(const uint8_t 
*data) welche nichts weiter macht als return(pgm_read_byte_far(data)).
Für alle anderen Architekturen steht da einfach nur "return *data;" 
drin.

Also mit einem ARM könnte das so aussehen:
sd_open_file()
sd_read_block()
EVE_cmd_loadimage(ziel, optionen, sd_block, gelesene länge)
wiederhole_bis_ende_der_datei
{
 sd_read_block()
 EVE_memWrite_sram_buffer(REG_CMDB_WRITE, gelesene länge)
}

Das gleiche müsste auch mit EVE_cmd_inflate() funktionieren.

Das sollte funktionieren, weil sowohl CMD_LOADIMAGE als auch CMD_INFLATE 
zwar die Daten direkt nach dem Kommando bekommen, aber beide anhand der 
Daten feststellen ob diese schon vollständig sind.

Alternativ gibt es für die FT81x die Möglichkeit CMD_LOADIMAGE mit einem 
Puffer im RAM_G zu benutzen, der Puffer wird mit CMD_MEDIAFIFO 
eingerichtet.
Irgendwo da oben im Thread ist ein Beispiel zum Mediafifo.
Mit CMD_INFLATE funktioniert das aber nicht.

Aber aussehen würde das so:
EVE_cmd_mediafifo(mediafifo_ptr, size)
sd_open_file()
EVE_cmd_loadimage(ziel, EVE_OPT_MEDIAFIFO, 0, 0)
wiederhole_bis_ende_der_datei
{
 sd_read_block()
 EVE_memWrite_sram_buffer(mediafifo_ptr, gelesene länge)
}

So mehr oder weniger aus dem Kopf, ist ewig her das ich MEDIAFIFO 
benutzt habe, ich fürchte auch gerade das ist deutlich aufwendiger und 
da müssen dann auch noch zwei Zeiger in den MEDIAFIFO verwaltet werden.
Zu erwähnen ist noch das die Adresse und die Länge für den MEDIAFIFO 
4-Byte aligned sein müssen.
Ach ja, mit PNG Bildern gibt es auch noch was u beachten, zum einen ist 
die Dekodierung super langsam im Vergleich zu JPG, dann ist EVE etwas 
wählerisch was das Format angeht und wenn man PNG lädt kann man RAM_G ab 
Adresse 0xF5800 nicht benutzen weil der Speicher zum Entpacken des 
Bildes verwendet wird.

Mit den BT81x kommt noch CMD_INFLATE2 dazu, das kann den MEDIAFIFO 
benutzen oder alternativ auch Daten aus dem FLASH vom Display.

von Rudolph R. (rudolph)


Lesenswert?

Zum Thema ESP32:
https://github.com/RudolphRiedel/FT800-FT813/issues/14

Letzter Beitrag da, ich gebe das erstmal auf, das führt irgendwie zu 
nichts.
Ja, man kann ESP-IDF Funktionen auch unter Arduino benutzen, leider wird 
das eher noch langsamer als mit dem esp32-hal-spi.c Treiber der Arduino 
Seite.

Aber mein letztes Problem war das ich DMA und nicht-DMA Transfers nicht 
mischen kann.

Ein paar Hundert Bytes per DMA zu verschicken ist super, etwas auf das 
ich nicht mehr verzichten möchte.
Ein paar Bytes per DMA zu verschicken ist albern, das Setup dauert 
länger als das eigentliche Senden.

von Johannes (Gast)


Lesenswert?

Hallo Rudolph,

noch ist die Entscheidung über den MC nicht gefallen. ATSAMC21N wäre 
eine Option. Ich benötige eine ganze Menge Hardware-UART.

Ich denke, ich werde ein Probeboard mit dem Chip machen. Gibt es bei den 
SAMs etwas besonders zu beachten? Sind die internen Taktgeber 
zuverlässig oder lieber Quarz?

Schließt du den FT81X genauso an wie bei einem 8Bit-AVR?

Ist das CAN vollständig on board oder wird ein Treiber benötigt?

Gruß,
Johannes

von Rudolph R. (rudolph)


Lesenswert?

Johannes schrieb:

>ATSAMC21N wäre eine Option. Ich benötige eine ganze Menge Hardware-UART.

Bisher habe ich "nur" die E, G und J verwendet, den J mit 64 Pins auch 
nur für die zwei CANs bzw. um eine Platine zu erstellen auf der sowohl 
ein SAME51J als auch ein SAMC21J bestückt werden können.

> Ich denke, ich werde ein Probeboard mit dem Chip machen. Gibt es bei den
> SAMs etwas besonders zu beachten? Sind die internen Taktgeber
> zuverlässig oder lieber Quarz?

Für CAN braucht man entweder einen sehr guten Resonator oder einen 
Quarz.
Ich verwende praktisch überall NX3225GB-16 (Digi-Key 644-1233-1-ND

Ein Kunde setzt in seinem Design für das wir Software liefern gerade 
einen Resonator ein, da bin ich gespannt wie das ausgeht.

> Schließt du den FT81X genauso an wie bei einem 8Bit-AVR?

Im Grunde genommen ja, mit QSPI kann ich an den EVE nichts anfangen.
Zum einen spiele ich keine Videos ab, zum anderen benutze ich DMA, bei 
meiner einfachen Demo braucht ein Display-Refresh mit dem E51 14µs.
Und ein Teil davon ist ein EVE_memRead16(REG_CMD_DL) für die 
Debug-Information das ohne DMA sechs Bytes über den SPI schiebt.

Das ist in der EVE_target.h zu sehen.
Wobei mein letzter Fehler auf einem Board war davon auszugehen das die 
SERCOMs von C21 und E51 gleich sind.
Blöderweise ist der E51 nicht ganz so flexibel, der kann SCK nur auf 
PAD1 legen, aber nicht auf PAD3.

Oh ja, zumindest bei den C21 sind die Ausgänge bei 3,3V zu schwach um 
ein Display mit mehr als nur ein paar MHz direkt treiben zu können, so 
über das Folien-Kabel mit den zwei Steckverbindungen.
Da verwende ich jetzt einen 74LVC2G17 für SCK und MOSI, sowie einen 
74VHC1GT125 für MISO.
Für direkt nur 3,3V auf 3,3V gehen sicher auch andere Teile, aber die 
Dinger habe ich eh da.

> Ist das CAN vollständig on board oder wird ein Treiber benötigt?

Für CAN wird praktisch immer ein Transceiver gebraucht, es gibt nur ganz 
wenig Controller die den eingebaut haben und mir fällt da gerade ein 
LPC11xx von NXP als Beispiel ein.

Hier, das war mein erstes C21 Board:
https://github.com/RudolphRiedel/SAMC21_one

Das Ding ist mit dem Transceiver und dem Spannungsregler Wakeup fähig.

An dem 7pol X5 habe ich so ein Board angeschlossen:
https://github.com/RudolphRiedel/EVE_display-adapter

Das L-D5019-01-02 hatte zusätzlich noch den gleichen Stecker.

Meine letzte Variante heißt L-D5019-06-02 und da sind neben dem Display 
Anschluss und ein wenig Logik noch zwei Stück TCAN1044V drauf für zwei 
Mal CAN-FD bis 8MBit/s, zwei Stück TLE7259-3GE für LIN, ein Schaltregler 
für die 3,3V und ein 5V LDO für den CAN.
Bestücken kann ich da einen ATSAMC21J oder einen ATSAME51J.

Eine von denen habe ich letzte Woche in ein 7" Display gesteckt mit 
einem E51 und einem CAN, vier Stück stecken mit C21 in 4.3" Displays und 
brauchen noch so ein paar Zeilen Code.

Was CAN angeht, das hier spielt soweit auch:
https://github.com/RudolphRiedel/USB_CAN-FD

Allerdings kämpft der Kollege noch damit das wir bei hoher Buslast 
Botschaften verlieren.
Nun ja, die Idee war ja auch nicht die Vector Tools zu ersetzen, sondern 
mehr so nach unten zu ergänzen.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.