Obsluha myši
Počítačová myš slouží primárně k určování pozice na obrazovce. Tato pozice je většinou označena grafickým symbolem, kterému říkáme kurzor myši. V následující části si popíšeme funkci pro změnu tvaru tohoto kurzoru.
Změna tvaru kurzoru myši
Při některých operacích s objekty v aplikaci je žádoucí mít možnost změnit tvar kurzoru myši. Konkrétní tvary kurzoru myši jsou systémově závislé, ale jejich význam může být v různých systémech stejný nebo podobný. Jako příklad si můžeme uvést kurzor, jenž uživatele upozorňuje na provádění časově náročnější operace. V operačních systémech Windows má tento kurzor (nechvalně) známý tvar přesýpacích hodin, zatímco u počítačů typu Apple se pro stejné upozornění používá kurzor tvaru hodin analogových.
Knihovna GLUT umožňuje vybrat tvar kurzoru myši z několika předdefinovaných vzorů, přičemž jejich konkrétní podoba závisí na použité platformě. Tvar kurzoru se změní voláním funkce glutSetCursor(int cursor). Tato funkce jako svůj argument vyžaduje číslo typu int reprezentující tvar kurzoru. S pomocí knihovny GLUT není možné vytvářet vlastní tvary kurzorů, ani modifikovat tvary přednastavené. Toto omezení vyplývá z toho, že na každé platformě se používá jiný, systémově závislý způsob definice kurzorů. V hlavičkovém souboru glut.h jsou definovány následující symbolické konstanty používané pro různé tvary kurzorů:
Symbolická konstanta | Význam |
GLUT_CURSOR_RIGHT_ARROW | šipka směřující doprava nahoru |
GLUT_CURSOR_LEFT_ARROW | šipka směřující doleva nahoru |
GLUT_CURSOR_INFO | symbol ruky s ukazujícím prstem |
GLUT_CURSOR_DESTROY | symbol pro uzavření resp. vymazání |
GLUT_CURSOR_HELP | symbol nápovědy, většinou otazník |
GLUT_CURSOR_CYCLE | symbol opakování, většinou šipky otáčející se v kružnici |
GLUT_CURSOR_SPRAY | láhev se sprejem |
GLUT_CURSOR_WAIT | symbol pro déletrvající operaci, hodiny |
GLUT_CURSOR_TEXT | kurzor tvaru velkého I, používaný pro vkládání textu |
GLUT_CURSOR_CROSSHAIR | zaměřovací kříž |
GLUT_CURSOR_UP_DOWN | symbol pro změnu vertikální velikosti, dvojitá šipka ukazující nahoru a dolů |
GLUT_CURSOR_LEFT_RIGHT | symbol pro změnu horizontální velikosti, dvojitá šipka ukazující doleva a doprava |
GLUT_CURSOR_TOP_SIDE | jednoduchá šipka ukazující nahoru |
GLUT_CURSOR_BOTTOM_SIDE | jednoduchá šipka ukazující dolů |
GLUT_CURSOR_LEFT_SIDE | jednoduchá šipka ukazující doleva |
GLUT_CURSOR_RIGHT_SIDE | jednoduchá šipka ukazující doprava |
GLUT_CURSOR_TOP_LEFT_CORNER | jednoduchá či dvojitá šipka ukazující do levého horního rohu |
GLUT_CURSOR_TOP_RIGHT_CORNER | jednoduchá či dvojitá šipka ukazující do pravého horního rohu |
GLUT_CURSOR_BOTTOM_LEFT_CORNER | jednoduchá či dvojitá šipka ukazující do levého spodního rohu |
GLUT_CURSOR_BOTTOM_RIGHT_CORNER | jednoduchá či dvojitá šipka ukazující do pravého spodního rohu |
GLUT_CURSOR_FULL_CROSSHAIR | zaměřovací kříž přes celou obrazovku (podobný se používá například v programu AutoCAD). Pokud není tento typ kurzoru systémem podporován (Windows), použije se GLUT_CURSOR_CROSSHAIR |
GLUT_CURSOR_NONE | neviditelný (resp. vypnutý) kurzor |
GLUT_CURSOR_INHERIT | tvar kurzoru se zdědí podle rodičovského prvku (používá se například u suboken) |
Ukázkový příklad číslo 7
V tomto příkladu je ukázána možnost změny tvaru kurzoru myši. Při běhu aplikace je možné pomocí kláves [a] až [w] nebo [A] až [W] měnit tvar kurzoru. Funkci glutSetCursor(int cursor) je možné volat, kdykoliv je aktivní nějaké okno. Typicky se používá změna tvaru kurzoru ve funkcích reagujících na akci uživatele. K dispozici je zdrojový kód sedmého příkladu a zdrojový kód se zvýrazněnou syntaxí.
Události generované při práci s myší
Při použití knihovny GLUT máme k dispozici celkem tři typy událostí, které jsou generovány při práci s myší. První typ události je generován při stisknutí nebo puštění některého z tlačítek myši. Druhý typ události je generován při pohybu myší se současně stisknutým tlačítkem. Třetí typ události se od druhého liší pouze tím, že je generován pouze při pohybu myši bez stisknutého tlačítka (takzvaný pasivní pohyb).
Ukázkový příklad číslo 8
V tomto příkladu je prezentován způsob registrace callback funkce volané při stisknutí či puštění některého z tlačítek myši.
Pro registraci této callback funkce je zapotřebí zavolat funkci glutMouseFunc(void (*func)(int button, int state, int x, int y)) z knihovny GLUT. Callback funkce musí mít čtyři argumenty, které jsou všechny typu int. První argument button specifikuje tlačítko, pro které je callback funkce volána. Hodnota tohoto argumentu může dle stisknutého či puštěného tlačítka nabývat tří číselných hodnot reprezentovaných symbolickými konstantami GLUT_LEFT_BUTTON (levé tlačítko myši),GLUT_RIGHT_BUTTON (pravé tlačítko myši) a GLUT_MIDDLE_BUTTON (prostřední tlačítko myši). Druhý argument state určuje, zda je dané tlačítko stisknuto, či puštěno. To je rozlišeno dvěma hodnotami reprezentovanými symbolickými konstantami GLUT_UP a GLUT_DOWN. Třetí a čtvrtý argument x, y určuje pozici kurzoru myši v okně v době vygenerování události.
Po startu příkladu se zobrazí šedý trojúhelník. Stisknutím libovolné kombinace tlačítek se mění barevné složky RGB u jednotlivých vrcholů (vertexů) tohoto trojúhelníka. Každému tlačítku myši je přiřazen jeden vrchol, proto je možné vytvořit až osm různých barevných kombinací.
Zdrojový kód osmého příkladu a zdrojový kód se zvýrazněním syntaxe.
Ukázkový příklad číslo 9
V tomto příkladu je prezentován způsob registrace callback funkce volané při pohybu myši se současně stisknutým tlačítkem na myši.
Pro registraci callback funkce volané při pohybu myši se stisknutým tlačítkem je zapotřebí zavolat funkce glutMotionFunc(void (*func)(int x, int y)). Callback funkce musí mít dva argumenty typu int. Tyto argumenty určují pozici kurzoru myši v době generování události. Za povšimnutí stojí, že z argumentů callback funkce není známo, které tlačítko myši je stisknuto. Pro rozlišení tlačítek musí mít aplikace zaregistrovanou i předchozí callback funkci (glutMouseFunc()), ve které se dozví veškeré informace o stisknutí či puštění tlačítek.
Callback funkce volaná pouze při pohybu myši (bez stisknutých tlačítek) se registruje pomocí glutPassiveMotionFunc(void (*func)(int x, int y)). Stejně jako předchozí callback funkce má i tato funkce dva argumenty typu int specifikující pozici kurzoru myši v okně v době generování události.
Po startu aplikace se zobrazí šipka. Při stisknutí levého tlačítka myši lze šipkou pohybovat, při stisknutí pravého tlačítka se šipka otáčí. Za povšimnutí stojí způsob rozhodnutí, která transformace (posun, či otočení) se má se šipkou provést v závislosti na předchozím stavu tlačítek myši při volání callback funkce registrované pomocí onMouseFunc(). Pro dojem plynulého pohybu objektu bez blikání by bylo vhodné použít tzv. double buffering, kdy je na obrazovce zobrazován obraz z jednoho bufferu, zatímco v druhém bufferu se počítá další obraz. Double bufferingem se budeme podrobněji zabývat v dalším dílu tohoto seriálu.
Zdrojový kód devátého příkladu a zdrojový kód se zvýrazněním syntaxe.
V dalším dílu si ukážeme základy animování s použitím časovače (timeru) a funkce idle.