Jak asi víte, psaní Wherigo her je realizováno pomocí programovacího jazyku LUA. V krátké sérii článků bych Vám chtěl přiblížit aspekty a výhody LUA jazyka, odpovědět na otázku, proč je pro Wherigo tak vhodný a také se naučit jeho specifika. Ačkoli je to značně nekomfortní, cartridge se dá napsat i rovnou ve zdrojovém kódu a dnes si asi tu nejjednodušší cartridge napíšeme.

lua_logo

LUA je vysokoúrovňový skriptovací jazyk, podobně jako třeba Javascript. V aktuální verzi 5.1 je vydán pod licencí GPL a proto ho můžete využívat i ke komerčním účelům zadarmo. Jeho největší výhodou je, že velice snadno spolupracuje s Céčkem a proto je velice vhodný jako nadstavba na již existující aplikaci pro uživatelské scriptování (a to i třeba pro Oregon, či Colorado, jejichž software je psaný také v céčku). Ač se možná zdá, že je to jazyk primitivní, opak je pravdou. LUA je moderní jazyk, na ukázku jmenuji pár buzzwords: garbage collector, dynamické typování, objekty (i když trochu jinak než je možná znáte), paralelní programování (!)… Krom Wheriga se s ním můžeme setkat ještě v mnoha počítačových hrách (Word of Warcraft, S.T.A.L.K.E.R., Crysis, Half-Life 2…) či programech (pluginy pro Apache server, editor SciTe, VLC media player a Adobe Photoshop Lightroom).

Pokud jste již na jazyk správně nalazeni, můžeme se pustit do krátkého úvodu. Budu předpokládat, že už jste někdy nějaký prográmek naprogramovali, a tudíž tušíte, co je to for cyklus, proměná atd. Základní aspekty LUA:

  1. příkazy ukončujeme koncem řádku, nepovinně můžeme používat i středník
  2. komentáře začínají dvěma pomlčkama –
  3. LUA je dynamicky typované, takže typ proměné je přiřazen k její hodnotě a ne k jejímu názvu, viz příklad
    1
    2
    3
    4
    5
    6
    7
    
    local x; --vytvoření lokální proměnné, není přiřazena hodnota takže ani typ
    local y;
    x = 10; --hodnotě 10 je přiřazen automaticky typ number
    y = "ahoj"; -- do proměnné y je přiřazena hodnota typu string
    print(x, y); -- vypíše obě proměnné
    print(x .. y); -- pomocí .. se spojují dva řetězce, v x je uložena hodnota typu number a proto se automaticky převede na string a pak se spojí
    print(x + y); --pokus o sečtení hodnoty number a string, skončí chybou
  4. bloky kódu se označují klíčovými slovy do a end (obdoba céčkovské syntaxe { a })
  5. standartně jsou všechny proměnné globální (nedoporučuji moc používat), lokální proměnnou deklarujeme klíčovým slovem local
    1
    2
    3
    4
    5
    6
    7
    8
    9
    
    x=10                              -- vytvoreni globalni promenne x
    print("globalni x=", x)        -- vytisknu obsah proměnné x
     
    do                                -- zacatek bloku
        local x=20                    -- vytvoreni lokalni promenne x, bude platná jen v bloku, kde je definovaná
        print("lokalni x=", x)      -- vytisknu obsah proměnné x
    end                               -- konec bloku
     
    print("globalni x=", x)         -- vytisknu obsah proměnné x, x už zase ukazuje na tu původní globální proměnou.

Tak, to by myslím mohlo pro začátek stačit (více příště) a teď už si naprogramujeme nejjednuduší aplikaci Ahoj světe. Je to opravdu velice jednoduché:

print("Ahoj svete");

Uvedený kód zkopírujeme do webového interpreta na adrese http://www.lua.org/cgi-bin/demo a stiskneme tlačítko Run. Vidíte, že to snad ani nemůže být lehčí. Zkuste si tam ještě zkopírovat oba ukázkové kódy uvedené výše a spustit.

Uvedená jednořádková aplikace se nám ale nespustí ve wherigu, pro vytvoření jednoduché cartridge ahoj světe musíme napsat řádek trochu více. Otevřete si libovolný textový editor a vložte do něj následující kód:

1
2
3
4
5
6
7
8
require "Wherigo"
cart = Wherigo.ZCartridge()
cart.Name="Ahoj Svete"
cart.StartingLocation = Wherigo.INVALID_ZONEPOINT
function cart.OnStart()
  Wherigo.MessageBox("Ahoj svete")
end
return cart

Nyní si tento kód řádek po řádku popíšeme (pokud to přestanete chápat, klidně tento výčet bodů přeskočte):

  1. Nalinkování Wherigo příkazů, na tomhle řádků nám skončí webový LUA interpret, protože Wherigo nezná
  2. Tady je to trochu složitější, nejprve tedy zjednodušeně:
    Řádek vytvoří instanci třídy Wherigo.ZCartridge a uloží do globální proměnné cart
    Ale protože LUA nepodporuje třídy, ve skutečnosti to udělá tohle:
    Wherigo je asociativní pole (neboli hashmapa) a syntaxe Wherigo.ZCartridge je syntaktická zkratka pro Wherigo["ZCartridge"] a tedy vrací prvek pole Wherigo pojmenovaný ZCartridge.
    ZCartridge vypadá, že je funkce, ale není tomu tak. ZCartridge je opět asociaticní pole, na kterém je definována metatabulka přetěžující operátor funkce – závorky. Když tedy napíšeme Wherigo.ZCartridge() zavolá se funkce __call z metatabulky, která je přiřazena asociativníjmu poli ZCartridge, které je uloženo v poli Wherigo
    kdo tenhle krok pochopil, nemusí číst následujících pár dílů seriálu :)
    Výsledek volání té funkce __call je přiřazen do globální proměnné cart. Je to opět asociativní pole (=tabulka). Tento krkolomný postup tu je použit na tvorbu objektů. LUA objekty standartně nepodporuje a jednou z možných implementací objektového programování jsou právě metatabulky. Více v dalších částech seriálu.
  3. Nastavím hodnotu pojmenovanou “Name“ v asociativním poli cart na hodnotu Ahoj svete. Objektově řečeno: Nastavím vlastnost Name mojí cartridge na hodnotu typu string „Ahoj svete“ (toto budu používat i níže)
  4. Nastavím vlastnost StartingLocation na objekt Wherigo.INVALID_ZONEPOINT  (v této konstantě je uloženo asociativní pole s metatabulkou (tedy vlastně objekt), které reprezentuje lokaci). INVALID_ZONEPOINT slouží k identifikaci playanywhere cartridge.
  5. Na objektu cart definuji funkci OnStart, která se volá vždy při spuštění cartridge
  6. Zavolám funkci Wherigo.MessageBox, která zobrazí hlášku uživateli.
  7. ukončení funkce
  8. vrátím mojí cartridge. Tohle musí být nakonci každého wherigo LUA kódu.

Vidíte i že takto jednoduchý kód je ve skutečnosti docela složitý, v další dílech seriálu se pokusíme dopracovat k jeho skutečné podstatě.

Vraťmě se k tomu textovému editoru, kde máme vložen náš zdrojový kód. Uložte ho jako soubor s příponou .lua. Spusťte Wherigo Builder, ale nedávejte File -> Open (tenhle zdroják nepůjde totiž otevřít, je pro Builder moc jednoduchý).
Místo toho zvolte Tools -> Compile a cartridge …, vyberte náš soubor .lua a zvolte kam se má cartridge uložit a pro jaké zařízení zkompilovat.
Nyní cartridge vyzkoušejte buď v emulátoru (Tools -> Emulator…) nebo třeba ve vašem Oregonu:

82  90
93

To bylo pro dnešek vše, pokusil jsem se Vás na LUA trochu nalákat, ukázat, že je to jazyk docela komplexní a mocný. V dalších dílech seriálu se podíváme hlouběji hlavně na tu tvorbu objektů, protože je to ve Wherigo hodně využíváno (jak vidíte i v našem jednoduchém příkladu.

Pokud budete mít k tomuto článku jakékoli dotazy, neváhejte je napsat do diskuse. Rovněž připomínky a nápady na další pokračování jsou vítány.

VN:F [1.9.5_1105]
Hodnocení: 4.3/5 (celkem 7 hlasů)
Tvorba cartridge rovnou v LUA, část 1., 4.3 out of 5 based on 7 ratings
Sdílej s přáteli:
  • Facebook
  • Twitter
  • Digg
  • del.icio.us
  • Google Bookmarks


Komentáře:
6 komentářů k článku "Tvorba cartridge rovnou v LUA, část 1."
PetrX napsal 25. 5. 2009 v 11:35

Perfektní tutoriál. Doufám, že bude pokračovat dál a já se konečně naučím programovat Wherigo a snad konečně nějaké vytvořím :-) . Jen tak dál


Maxinoha napsal 11. 6. 2009 v 13:50

Ahoj, vím že existuje zvýrazňovač syntaxe wherigo cartridge pod PSPad. Bylo by možné dát sem i odkaz ke stžení?


ProKesTom napsal 15. 11. 2009 v 15:14

Je nějaký nástroj na kontrolu chyb, který by označil chybu a ne se zhroutil, jako to dělá builder?


me2d09 napsal 19. 11. 2009 v 9:34

Bohužel ne, možná nějaký obecný kontrolor LUA syntaxe, ale 100% by neodhalil chyby se špatnou syntaxí Wherigo objektů, takže by to bylo polovičaté řešení.
Když Builder hlásí chybu, doporučuji mazat různé části kódu a dobrat se tak k tomu, kde ta chybka je…
A samozřejmě: zálohovat :)


zde napsal 15. 12. 2009 v 14:09

Opravdu je jedinné povinné API, které musí cartridge poskytovat atribut ‘startingLocation’, a metoda ‘onStart’?

Je někde referenční příručka na funkce, které lze z modulu Whereigo používat? (tj ten MessageBox apod)


[...] nejde? Je třeba si uvědomit, co přesně příkaz require dělá. Pokud jste četli první díl seriálu o LUA, víte že LUA je scriptovací jazyk a jako takový se nijak nekompiluje. GWC soubor není [...]


Zaslat komentář


2 + = eleven

Jméno: 
Email: 
URL: 
Text komentáře: