Temnota a světlo v GML

Ostatní jazyky GameMaker Efekty Temnota a světlo v GML

Dnes si ukážeme jak udělat ve hře temnotu a samozřejmě tu bude i světlo. Světlo v GM a GM:S začátečníci často řeší tak, že udělají černý sprite s dírou centrovanou na hráče. Inu, pro začátek to není špatné. Ovšem potom se dostáváme k problému "Co když tu bude jiný zdroj světla?", což toto řešení zcela rozbijí. Na druhou stranu pokročilý to řeší DLL knihovnami nebo vlastními Shadery, což má nevýhodu v tom, že to nemusí korektně zpracovat na všech platformách.

Dnes vás naučím jak vytvořit temnotu a světlo použitím vestavěných funkcí, což pracuje správně na všech platformách a podporuje více zdrojů světla.

Pro toto řešení budete potřebovat jen dva objekty a místnost.

oLightController

Vytvoříme si první objekt a pojmenujeme ho "oLightContro­ller".

Create

Vložíme do něj CREATE event a do nej napíšeme jediný řádek.

global.light = surface_create(view_wview,view_hview);

V tomto jediném řádku vytvoříme globální proměnnou s názvem light (ang. světlo), do této proměnné uložíme právě vytvořený surface s rozměry aktivního pohledu.

Pozn.: Globální proměnné mají výhodu, že nejsou obsaženy v žádném objektu, ale v samotné hře. Tudíž jdou volat nebo modifikovat odkudkoliv a existují i když objekt, který ji vytvořil, již neexistuje.

Step

Dále následuje STEP event. Do něj dáme tento kód.

surface_set_target(global.light);
draw_set_color(c_white);
draw_rectangle(0,0,view_wview,view_hview,false);
surface_reset_target();

Funkce surface_set_target(id) nastaví jako cíl vykreslování surface uložený v proměnné. Normálně nebo spíše bez definice se používá surface obsažený v okně programu. draw_set_color(col) nastaví na následující vykreslování určitou barvu, pamatujte, že z důvodu použitého blend módu (to až v draw eventu) bude světlejší barva dělat tmavší temnotu. Takže když chcete naprostou temnotu, použijte bílou barvu. Když chcete tmu napůl průhlednou, použijte šedou. Pokud tmu nechcete (například při den-noc cyklu), použijete černou. S funkcí draw_rectangle(x1,y1,x2,y2,outline) nakreslíte přes monitor tmu a nakonec funkce surface_reset_target() nastaví cíl vykreslování zpět na surface okna, ke které normálně nemáme přístup. I přes to, že máme surface plný tmy, zatím jej nevykreslujeme na monitor. To uděláme v DRAW eventu.

Draw

Vytvoříme si DRAW event a dáme do něj tento kód.

draw_set_blend_mode(bm_subtract);
draw_surface(global.light,view_xview,view_yview);
draw_set_blend_mode(bm_normal);

Funkce draw_set_blend_mode(bm_subtract) nastaví blend mód na subtract, což je hojně používané na efekty světla a tmy. Funkce draw_surface(id,x,y) vykreslí surface na monitor na zadaných souřadnicích, v našem případě to je levý horní roh aktivního pohledu. Jelikož surface má rozměry aktivního pohledu, tak pokryje celý pohled. Nakonec nastavíme blend mód zpět na normální.

oLightSource

Jako zdroj světla poslouží jiný objekt, nyní si vytvoříme nový objekt a pojmenujeme ho oLightSource.

Tento objekt bude mít jen jeden event a to END STEP event.

Step

Použitím End Step eventu zajistíme, aby se vykreslilo vše ostatní a až potom světlo. Kdybychom kód dali do STEP eventu, mohli bychom mít v budoucnu problém s depthem (např. světlo by se mohlo vykreslovat pod některými objekty). Takže si END STEP event vytvoříme a vložíme do něj tento kód.

size = 128;
draw_set_blend_mode(bm_subtract);
surface_set_target(global.light);
draw_ellipse_color(x-(size/2)-view_xview,y-(size/2)-view_yview,x+(size/2)-view_xview,y+(size/2)-view_yview,c_white,c_black,false);
surface_reset_target();
draw_set_blend_mode(bm_normal);

Pozn.: Tento kousek kódu je přizpůsoben tomu, aby jej šlo dát to scriptu, jen místo size, c_white a c_black použijete argumenty.

Proměnná size určuje jak velké naše světlo bude v pixelech. draw_set_blend_mode(bm_mode) nám nastaví blend mód na subtract. surface_set_target(id) nastaví cíl vykreslování na danou surface. Funkce draw_ellipse_color(x1,y1,x2,y2,col1,col2,outline) nám vykreslí světlo. Je použit jednoduchý výpočet, který nastaví velikost vykreslovaného světla podle proměnné size. Jelikož surface se pohybuje s pohledem (viz. olightController objekt), je potřeba od souřadnic elipsy odečíst x/y pohledu (jinými slovy, souřadnice budou relativní k souřadnicím pohledu). Potom tu jsou dvě barvy použité pro vykreslení. Dvě jsou proto, že barva elipsy je přechod, kde první barva bude uprostřed a druhá u kraje.

Tím je vše hotovo. Do místnosti si dejte oLightController a oLightSource. Pokud narazíte na problém, napište ho do komentáře, kde vám rád pomohu.

Temnota a stín v GameMakeru

Nakonec jsem vám připravil praktický příklad, v zipu naleznete projekt a spustitelnou aplikaci.

Doufám že jsem vás dnes naučil něco užitečného a nezapomeňte, vědění je od toho, aby se sdílelo.

Pokud se chcete o blend módech dozvědět více, můžete jít na YoYo games blog, první díl zde a druhý zde.


 

Stáhnout

Staženo 55x (2.14 MB)

 

  Aktivity (4)

Článek pro vás napsal Garrom Orc Shaman
Avatar
Autor se několik let zabýval tvorbě videoher v nástroji GameMaker. Poslední dobou se intenzivně učí používat Unity3D za použití jazyku C#..inu má se ještě hodně co učit.

Jak se ti líbí článek?
Celkem (2 hlasů) :
55555


 


Miniatura
Všechny články v sekci
GameMaker - Efekty

 

 

Komentáře

Avatar
bakuluk
Člen
Avatar
bakuluk:

Vývorný návod :) Nejlepší jaký jsem našel a moc děkuju :) Je jednoduchý ale efektní

 
Odpovědět 2. září 15:02
Avatar
Odpovídá na bakuluk
Garrom Orc Shaman:

Jsem rád že jsem ti pomohl :-)

Odpovědět 3. září 8:53
We're orcs, maybe we are not always wise or beautiful, but we will always be strong, outnumbered and well armed
Děláme co je v našich silách, aby byly zdejší diskuze co nejkvalitnější. Proto do nich také mohou přispívat pouze registrovaní členové. Pro zapojení do diskuze se přihlas. Pokud ještě nemáš účet, zaregistruj se, je to zdarma.

Zobrazeno 2 zpráv z 2.