====== Zadání ====== Navrhněte driver pro grafický řadič FT800 a kompatibilní. Možnosti driveru prakticky demonstrujte. Aplikace bude využívat dotykové ovládání, obsahovat vlastní textový font a umožňovat vykreslování widgetů. ====== Úvod ====== Cílem projektu bylo vytvořit C driver pro grafický řadič FT800 (a kompatibilní varianty). Driver by měl umožňovat naplno využívat možnosti chipu. Dále pak vytvořit ukázkovou aplikaci sloužící jako kostru pro další aplikace. Tato aplikace má implementovat všechny potřebné soubory a funkce pro použití vlastních fontů a bitmap. Dále pak má umožňovat změnu barevného schématu a jazyka použitého v aplikaci. ====== FT800====== Driver je určen primárně pro FT800. Tento řadič je specifický tím, že umožňuje tvorbu pokročilých GUI (grafických uživatelských rozhraní) s minimálními nároky na řídící mikrokontrolér. Obvod je připojován pomoci SPI (serial peripherial interface) s rychlostí až 30MHz nebo pomocí i2c (Inter-Integrated Circuit) do rychlosti 3.4MHz. Varianta FT800 umožnuje připojení displejů o rozlišení až 512x512 pixelů, přičemž každá barva je reprezentována 6-ti vodiči. Jde tedy o 18-bitovou hloubku (262144 barev). Obvod dále podporuje připojení rezistivní dotykové vrstvy. Uživateli pak poskytuje nejen souřadnice stlačeného bodu, ale také informaci o objektu na daných souřadnicích. Řadič dále umožňuje generování PWM mono audio signálu a je tedy vhodný i pro složitá GUI. Malé náročnosti pro řídící mikrokontrolér je dosaženo mimo jiné pomocí widgetů, což jsou složitější prvky, jako například tlačítka, posuvníky, hodiny, stavové ukazatele a mnohé další. Uživatelská aplikace může každému vykreslenému prvku nebo objektu přiřadit tag, který slouží jako identifikátor objektu. Následným sledováním tagu může aplikace zjišťovat, zda došlo k dotyku objektu a libovolným způsobem reagovat. Pro vykreslení obrazovky se vytváří DL (Display-list). Pro jeho tvorbu je vymezená paměť velikosti 8192B, do které může mikrokontrolér zapisovat příkazy a následně je nechat vykreslit pomocí dedikovaného registru. Do této paměti může ale zapisovat také grafický koprocesor, který vytvoří widgety. Proto není vhodné do této paměti zapisovat a využívat raději FIFO koprocesoru k vykreslování jednoduchých prvků i widgetů. Tento blok paměti má velikost 4096B a pro jeho obsluhu má řadič dva registry sloužící jako zapisovací a čtecí ukazatel. Zapisovací ukazatel musí po zapsání příkazů inkrementovat aplikace. Naopak čtecí ukazatel obsluhuje grafický koprocesor. Jsou-li si oba ukazatele rovné, znamená to, že všechny příkazy už byly zpracovány a zapsány do DL. FIFO je realizováno jako kruhový zásobník. Pro jednodušší aplikace lze využít některý z dostupných nástrojů umožňující vytvářet aplikace pomocí grafického prostředí nebo použití arduino knihovny. Nicméně ani jedno z těchto řešení se neukázalo pro vývoj aplikací příliš vhodné. {{https://www.digchip.com/companies_news/photos/ft800.jpg}} ====== Hardware ===== Driver je psán nezávisle na platformě. Pro použití v libovolné aplikaci je potřeba pouze správně nakonfigurovat soubor FT800 library_cfg.h (makra pro ovládání CS pro SPI, makra pro inicializaci SPI pro dvě různé rychlosti, definice datových typů, optimalizacční proměnné, velikost interního pole pro zpracování řetězců, rozlišení a typ displeje, ...). Pro použití pro jiný FTDI řadič je pak potřeba zkontrolovat a případně upravit nebo vyměnit soubor FT800 library.h který obsahuje mimo jiné definice adres registrů a mapování pamětí řadiče. ======= DRIVER ======== ===== Struktura driveru ===== Driver se skládá ze tří souborů. FT800 library.c - hlavní modul FT800 library.h - deklarace funkci hlavního modulu, definice registrů, adresace pamětí řadiče, parametry pro prvky a widgety FT800 library_cfg.h - konfigurace driveru specifická pro danou aplikaci a hardware ==== Hlavní modul ==== Modul obsahuje definice funkcí rozdělené do několika sekcí. Funkce pro : - zápis a čtení z registrů (7 funkcí) - tvorbu a řízení DL (3 funkce) - nastavení grafického kontextu (40 funkcí) - funkce pro koprocesor (45 funkcí) - uživatelské funkce (19 funkcí) První dvě sekce pro grafický kontext a koprocesor kompletně implementují api z dokumentu FT800 Series Programmer Guide, další sekce vznikaly postupně na základě potřeb během vývoje. === Funkce nastavené grafického kontextu === Tyto funkce mohou být použity přímo pro zápis do DL nebo mohou být použity prostřednictvým FIFO koprocesoru (preferovaná varianta). Návratová hodnota je vždy výsledkem logických operací mezi opcodem a parametry. Jednoduchým příkladem může být funkce line_width. uint32_t line_width(uint16_t width){ //sets width of line primitive in 1/16th pixel precision uint32_t temp=0; temp=(width)|(0x0E000000); return temp; } === Funkce pro koprocesor === Tyto funkce zapisují do FIFO koprocesoru, který následně vytváří DL. Veškereé widgety jsou umístěny v této části. Příkladem může být vykreslení tlačítka. Nejdříve je kontrolován staf FIFO, poté následuje opcode a parametry specifické pro daný příkaz (mapříklad souřadnice, rozměry, vypisovaný řetězec,...),nakonec je inkrementován zapisovací ukazatel FIFO (včetně zarovnání na 4B). void cmd_button(sint16_t x, sint16_t y,sint16_t w, sint16_t h, sint16_t font, uint16_t options,const char *s){ //draws a button uint32_t i=0; uint32_t read_addr; uint32_t write_addr; /* Waiting is needed to ensure that the coprocessor buffer does not overflow. BUFFER_RESERVE is used to make the program faster */ uint8_t wait_condition; do{ read_addr=rd16(REG_CMD_READ); write_addr=rd16(REG_CMD_WRITE); if(write_addr>=read_addr) wait_condition = ((write_addr-read_addr)>BUFFER_RESERVE?1:0); else wait_condition = ((write_addr+BUFFER_SIZE-read_addr)>BUFFER_RESERVE?1:0); }while(wait_condition); wr32(RAM_CMD+(write_addr),0xFFFFFF0D); wr16(RAM_CMD+((write_addr+4)&(BUFFER_SIZE-1)),x); wr16(RAM_CMD+((write_addr+6)&(BUFFER_SIZE-1)),y); wr16(RAM_CMD+((write_addr+8)&(BUFFER_SIZE-1)),w); wr16(RAM_CMD+((write_addr+10)&(BUFFER_SIZE-1)),h); wr16(RAM_CMD+((write_addr+12)&(BUFFER_SIZE-1)),font); wr16(RAM_CMD+((write_addr+14)&(BUFFER_SIZE-1)),options); while(*(s+i)!=0){ wr8(RAM_CMD+((write_addr+16+i)&(BUFFER_SIZE-1)),*(s+i)); i++; } wr8(RAM_CMD+((write_addr+16+i)&(BUFFER_SIZE-1)),*(s+i)); i++; wr16(REG_CMD_WRITE,(write_addr+16+i+3)&0xffc); } === Uživatelské funkce === Tato sekce se sice dále dělí na několik částí, nicméně obsahem všech jsou funkce, které souvisí s tvorbou GUI a jsou universálně použitelné pro různé projekty jako například : inicializace FT800, inicializace barev, inicializace řetězců, inicializace bitmamp a uživatelských fontů, kalibrace dotykové vrstvy, čtení tagu nebo souřadnic, konverze řetězců, inteligentní zalamování řetězců, počítadlo FPS, a další. ====== Možnosti aplikací ====== Driver byl použit již ve více projektech různé složitosti. Všechny aplikace jsou stejně strukturované a je tudíž velmi jednoduché vytvořit novou aplikaci. Postačuje zkopírovat několik souborů a pak už jen vytvářet jednotlivé obrazovky. Kostra nového projektu je tedy daná a je výsledkem postupného vývoje. Poutřebné soubory : - ftf.c,ftf.h,tft_cfg.h - hlavní modul ve kterém se nachází jednotlivé obrazovky - FT800 library.c, FT800 library.h, FT800 library_cfg.h - driver FT800 - tft_global_variables.h - strings.h - soubor s texty - font_data.h - soubor s daty pro font - bitmaps.h - soubor s daty pro bitmapy - tft_types.h - definice konfigurační struktury (jazyk,podsvit,barevné schema, ...) ==== Stavový automat ==== Aplikace je strukturována jako stavový automat se stavovou proměnnou scr. Jednotlivé obrazovky často přistupují ke stejným datům a většina proměnných je tak pro modul globálních. Během běhu programu je potřeba periodicky provádět některé operace jako například kontrola stavů časovačů nebo čtení tagu. Tyto operace jsou prováděny mezi vykreslením obrazovek z hlavní smyčky, která obrazovky volá. Obrazovky ("screeny") jsou tedy implementovány jako jednorázové vykreslení, ne jako smyčky. /* Touch handling */ ... /* Timers handling */ ... /* Screen state machine */ switch (scr) { //screens are not loops (they are called repeatedly) case MAIN_SCREEN: //MAIN screan main_screen(); break; case SETTINGS_SCREEN: //settings settings_screen(); break; case PASSWORD_SCREEN: //password password_screen(); break; case . . . } ==== Obrazovky (screeny),DL ==== Každé překreslení obrazovky je reprezentováno vykreslením jednoho displej listu (DL). Každý DL začíná voláním cmd_dlstart, dále pokračuje vykreslováním dalších příkazů s případnými výpočty. Ukončuje ho příkaz cmd(display()) a vykresluje ho cmd_swap(). Driver je koncipován bez vlastního zásobníku, tj. příkazy se posílají do FT800 přímo a je tedy možné mezitím provádět výpočty (např. souřadnic), což by při jednorázovém odeslání zásobníku nebylo možné. Navíc by bylo nutné alokovat 4KB SRAM, což by omezilo použití driveru pro menší mikrokontroléry. Obrazovky jsou vykresleny typicky s 20 až 70 FPS podle jejich složitosti. Příklad jednoduché obrazovky: cmd_dlstart(); /* Background gradient */ cmd_gradient_custom(COLOR_GR1); /* RGB type of color for the next commants */ cmd_set_color(COLOR_STR3,_COLOR_RGB); /* Print text to the center of the screen */ cmd_text(DISP_WIDTH/2,DISP_HEIGHT/2,28,OPT_CENTERX,"Hello World"); /* Draw button with tag 2, if it currently touched it is wrawned as flat */ cmd(tag(2)); cmd_button(5.5,20, 30, (atag==2)*OPT_FLAT,"Press here"); . . . /* End of DL */ cmd(display()); /* Draw */ cmd_swap(); ==== Fonty, bitmapy ==== FT800 má integrovány dva druhy fontů v několika velikostech. Pokud aplikace vyžaduje font například s českou diakritikou, je možné si tento font pomocí poskytovaného nástroje pro příkazovou řádku vygenerovat. K tomu je potřeba soubor fontu a textový soubor se znaky, které mají být vytvořeny. Výsledná data lze vložit například jako hlavičkový soubor do kódu. Dále je potřeba font do řadiče nahrát a správně jej inicializovat (custom_font_init). Aby bylo možné font použít, je nejdříve nutné konvertovat řetězce na správné kódování (znaky ve vytvořeném fontu jsou kódovány podle pořadí v textovém souboru před konverzí, kdežto řetězce v kódu jsou dány vývojovým prostředím). K tomu slouží další uživatelské funkce obsahující převod znaků podle kódovací tabulky. Podobně jako s fonty je možné dedikovaným nástrojem konvertovat bitmapy v různých formátech. Ty je následně potřeba, stejně jako fonty, nahrát do paměti a inicializovat (ardesa,rozměry, handle,formát,..). ==== Retězce, jazyky ==== Aby bylo možné měnit jazyk aplikace, obsahuje program vícerozměrné pole s adresami konstantních řetězců. První index určuje text (např. "Nastavení","Vytvořit položku",...), druhý index vybírá jazyk. ==== Barevná schémata ==== Podobně jako u řetězců obsahuje aplikace tabulku barev. První index určuje tzv. třídu (tlačítko typu jedna-BUT1, text typu 1 -STR1, bitmapy popředí -BMFG, gradient na pozadí GR11, atd..), druhý index par určuje složku RGB. Pro změnu barevného schématu stačí předat driveru adresu jiné tabulky barev. Jelikož grafický kontext používá tři druhy barev (COLOR_RGB,FGCOLOR,BGCOLOR), byla v ytvořena funkce cmd_set_color, která nastavování zjednodušuje. ====== Demonstrace funkcí ===== Následující video demonstruje široké možnosti vytvořeného driveru a možnosti aplikace. Tento konkrétní projekt realizuje nízkonapěťovou část spínacích hodin. Tato komplexní aplikace je postavena na 8-bitovém mikrokontroléru z řady ATXMEGA. {{youtube>gMtHJN_q7O8?medium}} Na následujících snímcích je vidět hardware vytvořený v rámci diplomové práce a ukázková aplikace. Tato zařízení jsou řízena pomocí mikrokontrolérů s jádry ARM (STM - STM32F030CC) realizují vývojové desky pro bezdrátový přenos audio signálu ve standardu WiSA. Jelikož konkrétní aplikace je zatím ve vývoji, byla pro demonstraci pouze přeportována jiná aplikace, která ukazuje, že vytvořená driver je možné použít pro různé platformy. {{:2016:tx.jpg?300|}} {{:2016:rx.jpg?300|}} {{:2016:imag0148.jpg?600|}} ====== Závěr ====== Projekt popisuje vytvořený driver umožňující plné využití grafického řadiče FT800. Software je universálné a může být použit pro libovolnou platformu. Tento řadič spolu s vytvořeným ovladačem umožňuje tvorbu pokročilých GUI při minimálních nárocích na mikrokontrolér. Software byl již využit pro několik profesionálních produktů, na dalších se pracuje a další jsou v plánu (vztaženo k datu vytvoření tohoto dokumentu).