GUI
GUI
1. srpna 2002, 00.00 | Seznamte se blíže s knihovnou SDL. Tímto článkem dokončíme programování console a vrhneme se na základy "opravdového" GUI.
{Filtrování kláves}
Jak jsem v minulém díle slíbil, dnes dokončíme programování
console a vrhneme se ne začátky GUI. Vezměme to tedy hezky po pořádku.
Z minulého článku nám zbývá filtrování kláves a popsání funkcí,
měnících vlastnosti console. K načtení kláves a jejich zpracování
použijeme již zmíněnou knihovnu SDL (naleznete ji na www.libsdl.org).
Filtrování kláves
Knihovna SDL ukládá veškeré události do
SDL_Event, ať jde o
pohyb myší, poslání žádosti o zavření okna, atd. Musíme si tedy
vytvořit proměnnou tohoto typu (
SDL_Event event). Doporučuji
ji začleňovat do třídy console, co když budeme chtít filtrovat
události i v jiné části programu (např.
EDITBOXY).
Do třídy console přidáme pouze tyto dvě věci:
class C_CONSOLE
{
public:
...
int Run(SDL_Event * event);
int Poll_Events(SDL_Event * event);
...
};
|
|
Funkce int Run(SDL_Event*)
zavolá funkci int Poll_Events(SDL_Event*), která přefiltruje klávesy
a následně je zavolána funkce int Draw();, která consoli vykreslí.
Celou dobu tady píši o nějakém filtrování událostí, kláves, atd.
Ale ještě jsem vám neřekl, jak je do proměnné event
"nacpeme". Před spuštěním fce. int Run(SDL_Event*);
(v našem případě Run(&event);) zavoláme funkci SDL_PollEvent(event);,
která proměnnou event naplní. Nesmíme však zaměnit
fci SDL_PollEvent za SDL_WaitEvent. Rozdíl je dosti podstatný.
První funkce naplní proměnnou aktuálními událostmi, kdežto funkce
druhá vyčkává na první událost, která se od jejího zavolání stane.
Ve výsledném efektu by program "zamrzl" dokud by jsme nestiskli klávesu,
pohli myší nebo joystickem. Pro snadnější načítání znaků z
klávesnice také aktivujeme konverzi UNICODE a to
příkazem SDL_EnableUNICODE(TRUE).
Popišme si tedy ony dvě funkce:
int C_CONSOLE::Run(SDL_Event * event)
{
Poll_Events(event); -prefiltrujeme klavesy
Draw(); -konsoli vykreslíme
return FCE_OK; -vše je v pořádku, tak to oznámíme
};
int C_CONSOLE::Poll_Events(SDL_Event * event)
{
int i;
static int command_pos = -1; -aktualni pozice v retezci, do
ktereho zadavame prikazy
if(event->type == SDL_KEYDOWN) -zjistime, zda jde o stisk
klavesy
{
switch (event->key.keysym.sym) -zde budeme
porovnavat scancody klavesnice
{
case SDLK_PAGEUP: -posouvame se v
historii vypisu
{
act_line++; -zvetsime
index prvni zobrazovane radky
if(act_line + max_display_lines >= line_count)
-ohlidame, aby jsme nepresahovali pres hranici historie vypisu
act_line = line_count - max_display_lines - 1;
-zasahujeme mimo, musime to opravit
if(act_line < 0) act_line = 0;
-zasahujeme mimo, musime to osetrit
break; -vse je hotovo
};
case SDLK_PAGEDOWN: -to same jako
pro PAGE UP, akorat dolu
{
act_line--;
if(act_line < 0) act_line = 0;
break;
};
case SDLK_END: -tato klavesa nas
jaksi nezajima
break;
case SDLK_DOWN: -sipkou dolu se
budeme poybovat v historii prikazu
{
if(command_history_count < 1) break;
-pokud nejsou zadne prikazy v historii, neni cim posouvat
act_command_history++; -zvetsime
index o 1 (posuneme se nahoru)
if(act_command_history >= command_history_count) act_command_history = 0;
-osetrime hranice historie
strcpy(command,command_history[act_command_history]);
-zkopirujeme prikaz z historie do prikazove radky
break; -hotovo
}
case SDLK_UP: -to same akorat pro
sipku nahoru
{
if(command_history_count < 1) break;
act_command_history--;
if(act_command_history < 0) act_command_history = command_history_count - 1;
strcpy(command,command_history[act_command_history]);
break;
}
case SDLK_BACKSPACE: -mazeme
aktualni prikaz
{
command[command_pos] = '\0';
-na misto v retezci, kde je zrovna kurzor ulozime znak \0 -
nevypisuje se
command_pos--; -a
posuneme se o jedno misto zpatky
if(command_pos <= -1) command_pos = -1;
-musime si dat pozor, aby jsme nemazali mimo exitujici retezec (napr.
pozice -1 je dosti zajimava)
break;
}
case SDLK_TAB: -tato klavesa nas
opet nezajima
break;
case SDLK_KP_ENTER : -pro klavesy
ENTER a ENTER na numericke klavesnici plati stejne prikazy, proto
nesmime za tento radek doplnit break; (takto automaticky skoci na
dalsi radku
case SDLK_RETURN:
{
act_line = 0; -pravdepodobne
neco pribyde do historie vypisu, tak nastavime aktualni vypisovanou
radku na prvni (kdyby jsme nahodou meli odscrollovano)
act_command_history = -1; -to
same plati i pro historii prikazu
command_history_count++; -do
historie prikazu pribyde dalsi prikaz
if(command_history_count >= CONSOLE_COMMAND_HISTORY_MAX) command_history_count = CONSOLE_COMMAND_HISTORY_MAX;
-co kdyby byla historie jiz plna
//posuneme radky
historie o jednu uroven niz tak, aby nejaktualnejsi byla na zacatky
pole
if(command_history_count >= 2)
-pokud je jen jeden prikaz, nemusime nic posouvat cyklem
{
for(i = command_history_count - 1; i >= 1; i--)
{
strcpy(command_history[i],command_history[i - 1]);
-prekopirujeme retezce
};
}
strcpy(command_history[0],command);
-a tady nahrajeme aktualni prikaz na prvni misto
//provedeme prikaz
Run_Command(command,command);
-prvni je jmeno prikazu a druhe jsou jeho parametry (sam si je ze
zadaneho prikazu vypreparuje)
for(i = 0; i < CONSOLE_CHAR_PER_LINE; i++)
{
command[i] = '\0';
-ted vymazeme prikazovou radku
}
command_pos = -1; -nastavime
index kurzoru prikazove radky na zacatek
break; -hotovo
}
// ted nas cekaji
klavesy na numericke klavesnici
case SDLK_KP0 :
case SDLK_KP1 :
case SDLK_KP2 :
case SDLK_KP3 :
case SDLK_KP4 :
case SDLK_KP5 :
case SDLK_KP6 :
case SDLK_KP7 :
case SDLK_KP8 :
case SDLK_KP9 :
case SDLK_KP_PERIOD: - toto je .
case SDLK_KP_DIVIDE: -toto je /
{
if(act_command_history != -1)
- pokud jsme prochazeli hostorii prikazu a chceme nyni psat, je
dobre si prikazovou radku nejprve vymazat
{
command_pos = -1;
for(i = 0; i < CONSOLE_CHAR_PER_LINE; i++)
{
command[i] = '\0';
}
act_command_history = -1;
};
command_pos++; -posuneme
si index kurzoru o jednu pozici doprava
if(command_pos >= CONSOLE_CHAR_PER_LINE) command_pos = CONSOLE_CHAR_PER_LINE - 1;
-zjisitme si, zda nezapisujeme mimo hranici retezce prikazove
radky
if(event->key.keysym.sym == SDLK_KP_PERIOD) command[command_pos] =
(char)'.'; - tyto znaky nejsou osetreny UNICODE, doplnime je
tedy "natvrdo"
else
if(event->key.keysym.sym == SDLK_KP_DIVIDE) command[command_pos] =
(char)'/';
- -----|
|-----
else
command[command_pos] = (char)(event->key.keysym.sym - 256) + '0';
- a tady je jiz konverze scancodu na znak. 256 je pozice od ktere
se pocita NUMERICKA klavesnice a '0' je index 0. Takto zkonvertovany
znak ulozime do retezce prikazove radky
break; -vse hotovo
};
default: -standatrni klavesa
if(event->key.keysym.unicode)
-pokud se jedna o UNICODE znak, neni co resit
{
//zde plati to same jako u predesleho zapisovani, proste vymazeme
prikazovou radku, pokud jsme se stourali v historii prikazu
if(act_command_history != -1)
{
command_pos = -1;
for(i = 0; i < CONSOLE_CHAR_PER_LINE; i++)
{
command[i] = '\0';
}
act_command_history = -1;
};
command_pos++;
-posuneme si index kurzoru v retezci prikazu
if(command_pos >= CONSOLE_CHAR_PER_LINE) command_pos = CONSOLE_CHAR_PER_LINE - 1;
-osetrime, zda nezapisujeme mimo hranici retezce prikazove redky
command[command_pos] = (char)event->key.keysym.unicode;
-zapiseme znak. Do event->key-keysym.unicode se uklada jiz
pretrasformovany znak ze scancodu do char. !!!Pozor!!! musi byt
zapnute SDL_EnableUNICODE(true);
}
}
}
return FCE_OK; -a mame to za sebou
};
|
|
Funkci int Poll_Event(SDL_Event*) použijeme s menší úpravou i v
objektu C_EDIT_BOX, ale to až dále. Nyní jsme
dokončili poslední z důležitých funkcí pro práci s consolí. Zbývají
nám jen funkce, pomocí kterých budeme měnit vlastnosti console, jako výšku,
šířky, pozici, barvy. Napíšeme si pouze jejich funkční prototypy
(aby jsme měli celou třídu C_CONSOLE úplnou),
tělo funkce je velmi jednoduché. Prostě v nich naplníme proměnné
jako bkg_img_ID nebo line_color, atd.
class C_CONSOLE
{
public:
...
...
//SET COLORS
int Set_Background_Color(float r,float g,float b,float alpha);
int Set_Background_Color(T_COLOR_RGBA color);
int Set_Border_Color(float r,float g,float b,float alpha);
int Set_Border_Color(T_COLOR_RGBA color);
int Set_Text_Color(float r,float g,float b,float alpha);
int Set_Text_Color(T_COLOR_RGBA color);
//SET SIZE AND POSITION
int Set_Size(float width,float height);
int Set_Position(float X,float Y);
int Set_Font_Size(float to);
//SET BACKGROUND IMAGE PROPERTIES
int Set_Image_Texture(char file[]);
int Set_Image_Texture(int ID);
int Set_Image_Position(int x1,int y1,int x2,int y2);
int Set_Image_TexCoords(float tx1,float ty1,float tx2,float ty2);
int Set_Image_Color(float r,float g,float b,float a);
};
|
|
[-more-]{GUI}
GUI
Tímto máme za sebou celou třídu C_CONSOLE. Jak jsem již
psal v minulém článku do koncepce GUI jako takového příliš
nezapadala, ale pro tvůrce her může být užitečná. Co se týká
GUI samotného máme před sebou docela slušný kus práce. Zapomeňme
teď na konkrétní názvy jako tlačítka (buttony), zaškrtávátka (checkboxy),
atd. Nazvěme je souhrnně objekty GUI. Každý objekt GUI bude určitého
typu, tzn. přiřadíme mu určitou třídu. Všechny třídy
jak pro tlačítka, zaškrtávátka, atd. mají mnoho společných věcí.
Můžeme začít od pozice, velikosti, barvy, velikosti fontu, názvu,
ID vlastníka, funkcí pro vykreslování a testování myši. Také všechny
objekty GUI uložíme do jednoho velkého pole, abychom si ušetřili práci
se samostatným polem pro tlačítka nebo popisky. Díky těmto faktorům
jsem se rozhodl pro použití jednoho mateřského objektu od kterého zbylé
objekty odvodíme. Nadefinujme si tedy objekt pod názvem C_GUI_OBJECT
class C_GUI_OBJECT
{
public:
int x,y,width,height; -pozice a velikost
char name[GUI_OBJECT_NAME_LEN_MAX]; -jmeno obejktu (napr.
"Koupit"), pomocí tohoto nazvu objekt v poli vyhledame
char visible; -je videt ci ne
char mouse_state; -co zrovna dela myska (je nad objektem,
je nad objektem stisknuta, ...)
float font_size; -velikost fontu
char owner_ID; -ID vlastnika v poli, zpravidla pujde o
objekt C_MENU, ale to az dale
char used; -jestli je tato pozice v poli pouzita ci ne
char type; -o jaky typ objektu se jedna (tlacitko,
zaskrtavatko, popisek, ...) je to velmi dulezite, ale to si popiseme
az dale
char func_name[GUI_FUNC_NAME_LEN_MAX]; -jmeno volane funkce
(napriklad pri stisku tlacitka, atd.)
T_GUI_FUNC function; -odkaz na funkci, ktera se ma provest
po ... (stejne jako u console)
virtual int Draw(void) = 0; -funkce pro vykresleni
virtual int Test(int mouse_x,int mouse_y,int left_but) = 0; -funkce
pro otestovani pozice a tlacitek mysi
};
|
|
Vše je to moc hezké až na jednu věc. Právě
jsem vám zahltil hlavu hromadou "neznámých" věcí. Například
owner_ID. Jak jsem psal výše, všechny objekty se uloží do jednoho
pole vytvořeného z ukazatelů na
C_GUI_OBJECT. Jelikož ostatní
objekty budou od této třídy odvozeny (sama existovat nemůže, musí
být vždy předkem), mohou ji "zastoupit". Zděděné
objekty budou vlastnit funkce
Draw() i
Test(), potřebné pro
práci s nimi. Jakmile ale přiřadíme do pole objekt od tohoto objektu
odvozený, ztratíme informace o potomkovy a budeme mít přístup pouze k
proměnným a metodám (funkcím) předka (pokud tento objekt opět
nepřetypujeme zpět, ale to až dále). Jenže funkce potřebné
pro vykreslení objektu a jeho otestování předek již obsahuje, nebude s
tím žádný problém a práce se nám velmi zjednoduší.
owner_ID je
tedy ID vlastníka. Zpravidla půjde o objekt typu
C_MENU, který
bude odvozen od
C_GUI_OBJECT. Pokud bude mít
C_MENU (vlastník)
proměnnou
visible nastavenou na
false, nevykreslíme ani
objekt, pro který je objekt
C_MENU vlastníkem. To je dosti kostrbatě
napsané, ale doufám, že to pochopíte. Vše podrobně popíšu, až se k
tomu prokoušeme. Další věcí je odkaz na funkci, která se má provést
po splnění určité, objektu typické vlastnosti. U tlačítka půjde
o stisknutí, u zaškrtávátka zaškrtnutí nebo u editboxu stisknutí klávesy
Enter. Funkční prototyp se bude od toho, který jsme použili u
console trochu lišit. Jelikož různé funkce budou vyžadovat různé
parametry, rezervujeme si tři čísla typu
int (například
pozice kurzoru a tlačítka při zavolání funkce) a jeden ukazatel na
void
(void * data), který můžeme použít (po přetypování na
char
* například k uložení řetězce editboxu).
Definice, definice, definice
Proměnné mouse_state,
type, atd. mohou nabývat různých číselných hodnot, navrhuji
proto zavedení jistých definic :
DEFINICE PRO PRACI S RETEZCI A POLI
RETEZCU (viz. dale)
#define GUI_CAPTION_LEN_MAX 50 - maximalni delka nazvu (zobrazeneho,
napr napis na tlacitku)
#define GUI_OBJECT_NAME_LEN_MAX 100 -maximalni delka retezce do
ktereho ulozime jmeno objektu (pro vyhledavani v poli)
#define GUI_FUNC_NAME_LEN_MAX 100 -maximalni delka nazvu(retezce)
funkce (slouzi pro nahravani a doplneni podle tabylky funkci)
#define GUI_STRING_LEN_MAX 101 -maximalni delka retezce, je to 100
znaku plus 1 ukoncovaci
#define GUI_LIST_BOX_LINES_MAX 100 -maximalni pocet radek v
listboxu (az dale)
//101 = 100 chars + 1 ending
typedef (*T_GUI_FUNC)(int a,int b,int c,void * pointer = NULL); -definice
ukazatele na funkci, void * pointer nastavime defaultne na NULL -
zadne dalsi parametry, za behu programu se to da velmi snadno zmenit
#define GUI_OBJECT_MAX 500 -maximalni pocet obejktu jednoho GUI
TOTO JSOU NAZVY JEDNOTLIVYCH TYPU OBJETU V GUI, ulozime je do C_GUI_OBJECT::type
#define GUI_BUTTON 1
#define GUI_LABEL 2
#define GUI_MENU 3
#define GUI_CHECK_BOX 4
#define GUI_EDIT_BOX 5
#define GUI_IMAGE 6
#define GUI_SCROLL_BAR 7
#define GUI_LIST_BOX 8
#define GUI_FRAME 9
#define GUI_BUTTON_DOWN 1
#define GUI_BUTTON_UP 2
TOTO JSOU PARAMTERY FUNKCE PRO VYHLEDAVANI V POLI PRI NAHRAVANI
#define GUI_FREE_POSITION 1 -najde prvni
volnou pozici a vrati jeji ID
#define GUI_LAST_USED_POSITION 2 -najde posledni pouzitou pozici a
vrati jeji ID
#define GUI_FIRST_USED_POSITION 3 -najde prvni pouzitou pozici a
vrati jeji ID
BAREVNA SCHEMATA (to az dale)
#define GUI_NORMAL 0 -normalni vykresleni
#define GUI_HIGHLIGHTED 1 -barva kdyz je mys nad objektem
#define GUI_DOWN 2 -barava, kdyz jsme nad objetem stiskli tlacitko
mysi a stale ho drzime
#define GUI_SELECTED 2 -barava pri vybrani objektu (napr. editbox
- psani)
POZICE MYSI A KLACESNICE ulozime do C_GUI_OBJECT::mouse_state
#define GUI_LEFT_MOUSE 0 -leve mysitko
#define GUI_RIGHT_MOUSE 1 -prave mysitko
#define GUI_MIDDLE_MOUSE 2 -prostredni mysitko
#define GUI_MOUSE_MOVE 3 -mys je nad objektem, zadne tlacitko neni
stisteno, pouzije se barevne chema GUI_HIGHLIGHTED
#define GUI_NOTHING 4 -mys neni nad objektem
#define GUI_ENTER 5 -byl stisknuty ENTER
#define GUI_KB_UP 6 -stisknuta sipka nahoru
#define GUI_KB_DOWN 7 -stisknuta sipka dolu
#define GUI_MOUSE_DOWN 8 -tlacitko na mysi bylo stisknuto
|
|
Toto je většina definic, některé jsou pro nás zatím zbytečné,
ale chtěl jsem, aby jste si udělali nějaký obrázek o tom, jak
to bude asi vypadat a co se kam bude ukládat. Nejsou zde obsažený definice
pro
scrollbary, neboť na ty máme ještě dost času.
[-more-]{První třída/objekt GUI}
První třída/objekt GUI
Ve hře
můžeme mít několik GUI najednou, nebylo by proto moudré ukládat
objekty GUI do globálního pole. Vytvoříme si tedy objekt C_GUI
pomocí kterého budeme vše obsluhovat. Podle mého názoru by mohl vypadat asi
takto:
class C_GUI
{
public:
C_GUI_OBJECT * object_array[GUI_OBJECT_MAX]; -pole do
ktereho ulozime objekty GUI
C_GUI_OBJECT * focus; - ukazatel na aktualne vybrany objekt
(napriklad stisknute tlacitko), jeho funkci si popiseme pozdeji
int Init(void); -nastavi GUI
int Clear(void); -vymaze GUI
int Hide_All_Menus(void); -skryje vsechna menu
int Load_Menu(char file[]); -nahraje menu
int Find_Position(int which); -najede pozici podle kriteria
(viz. vyse - GUI_FREE_POSITION,...) a vrati jeji ID
int Draw(void); - vykresli GUI
int Edit_String(char text[GUI_STRING_LEN_MAX],int& act_pos);
-postara se o editaci retezce (napriklad pro editbox), je to
podobne jako u console
int Bind_Function(char func_name[GUI_FUNC_NAME_LEN_MAX],T_GUI_FUNC
func); -"navaze"/priradi objektum, ktere maji jmeno
funkce func_name, funkci func
};
|
|
V šedém rámečku je pouze nutný základ, postupem času ho budeme rozšiřovat o přístupové
funkce k objektům GUI, k nahrávání a rozšířenému vykreslování.
Funkce
Init() zavolá funkci
Clear(), která vymaže pole GUI
objektů (
object_array[]) a vymaže
focus (nastaví ho na
NULL).
K čemu budeme
focus potřebovat? Tato otázka je opravdu na místě.
Představte si situaci, kdy kliknete na tlačítko, ale myš nepustíte,
popojedete mimo tlačítko a pustíte. V momentě, kdy najedete na talčítko
a myš zmáčknete (myslím tím tlačítko), do
focus se uloží
ukazatel na GUI objekt na kterém k této akci došlo. To nám velmi ulehčí
práci. V případě, že neklikneme na žádný objekt, bude hodota
fucus
rovna
NULL, pokud se stisklým tlačítkem myši poté najedeme například
na tlačítko a pustíme, jednoduše otestujeme, zd byla myš stisknuta na
tlačítku nad kterým byla puštěna. Prostě porovnáme ukazatel
focus
a ukazatel na GUI objekt, který je uložený v
object_array[]. Stejným
způseb zjistíme, zda máme provést nějakou akci po uvolnění
tlačítka myši. Po odchycení kódu pro uvolnění tlačítka (popíšeme
si níže), otestujeme, jestli je myš nad nějakým objektem, respektive
nad objektem, nad kterým byla stištěna. Stačí k tomu jednoduchá
podmínka :
if(focus->mouse_state == GUI_MOUSE_DOWN) focus->func(x,y,tlacitko,data);
Podobných příkladů je nespočet, každý si popíšeme až u
konkrétního objektu. Ve třídě
C_GUI se také objevila funkce
Load_Menu(), která má prý nahrávat menu ze souboru
file[]. Po
jisté době jsem dospěl k závěru, že vlastnosti jednotlivých
objektů (pozice, barva, velikost,...) bude lepší uchovávat mimo zdrojový
kód, jelikož pro jejich změnu stačí upravit menší skript a nemusíme
kompilovat znovu celý program. Díky tomuto můžeme velmi jednoduše měnit
skiny našeho GUI. Jediné co musí být zadané v programu je tabulka
funkcí, které se po nahrání GUI přiřazují jednotlivým objektům.
Skript je velmi jednoduchý, ale k jeho úplnému pochopení budeme potřebovat
znát jednotlivé objekty GUI. Vše si samozřejmě popíšeme a vysvětlíme,
až na to nastane ten správný čas, respektive až budeme znát ten či
onen objekt. Ukáži vám jeden demonstrační skriptík, na kterém si později
budeme vysvětlovat jednotlivé objekty GUI. Nelamte si tedy hlavu, když mu
nebudete rozumět, neboť vše má svůj čas. Tak tady je :
#MENU [menu1] -timto dame najevo, ze nahravame menu (objekt C_MENU) s
nazvem [menu1]
{
ZDE NASTAVIME BAREVNE SCHEMA MENU
#line_color 1.0 1.0 1.0 1.0
#line_move_color 1.0 1.0 0.0 1.0
#line_down_color 0.0 0.0 1.0 1.0
#button_color 0.0 0.0 0.0 0.0
#button_move_color 1.0 1.0 0.0 0.5
#button_down_color 1.0 0.0 0.0 0.5
#text_color 1.0 1.0 1.0 1.0
#text_move_color 1.0 1.0 0.0 1.0
#text_down_color 1.0 0.0 0.0 1.0
#scrbar_back_color 0.5 0.5 0.5 1.0
#edit_color 0.8 0.8 0.8 0.5
#edit_move_color 0.5 0.5 0.5 0.5
#edit_selected_color 1.0 1.0 1.0 0.5
#edit_font_color 1.0 1.0 1.0 1.0
#edit_font_move_color 1.0 1.0 0.0 1.0
#edit_font_selected_color 0
#FRAME [menu2_frame] -toto je ramecek se jmenem [menu2_frame], bude
obklopovat tlacitko
-1,430,105,45 -jeho pozice (x,y,sirka,vyska)
1.0 1.0 1.0 1.0 -barva okrajove cary
1.0 1.0 0.0 0.5 -barva vyplne
#LABEL [manu_label2] -popisek
10,435 -pozice (x,y)
MENU2 -text popisku
0.5 -velikost fontu
0.8 0.8 0.8 1.0 -barva textu
#BUTTON [console] -tlacitko, pokud ho budeme chtit najit v poli
objektu GUI, jmeno pro hledani je [console]
10,450,90,20 -pozice (x,y,sirka,vyska)
Show_menu1 -text tlacitka
0.5 -velikost fontu
Show_menu1 -jmenu funkce, ktera se spusti po stisknuti tlacitka
};
|
|
Takto nějak vypadá skript GUI, který budeme používat. Jak
jste si jistě všimli, každý objekt
C_MENU shlukuje objekty ostatní
a má vlastní barevné schéma. V tomto případě je uloženo tlačítko
s nápisem
"Show_menu1", okolo něj je rámeček se žlutým
pozadím (
r = 1,g = 1,b = 0) a bílou okrajovou
linkou. Uvnitř toho rámečku je ještě popisek
"MENU2".
Měli bychom si tedy nadefinovat objekty
C_MENU(menu),
C_FRAME(rámeček),
C_LABEL(popisek),
C_BUTTON(tlačítko). Dále funkce sloužící k
jejich nahrání a obsluze. Ale říká se, že v nejlepším se má přestat.
Nuže těším se na vás u dalšího dílu seriálu Jak vyzrát na GUI.