Egy összetett GameObject sok-sok gyerek GameObject-bĹ‘l állhat bonyolult hierarchiában. Ezen belĂĽl egy gyerek GameObject-et sok komponens Ă©s komponensenkĂ©nt számtalan beállĂtás Ăr le.
TĂ©telezzĂĽk fel, hogy ez a bizonyos bonyolult GameObject a játĂ©kunkban egy több helyen elĹ‘fordulĂł dolgot Ăr le, mint pĂ©ldául egy gyakori ellenfelet. Akár többszáz helyen elĹ‘fordulhatnak ezek a GameObject-ek elosztva sok Scene-ben. Ha ezen ellenfelek mindegyikĂ©t szimpla másolással hoztuk lĂ©tre egy eredetibĹ‘l, akkor a legminimálisabb változtatást a GameObject-en többszáz helyen kĂ©ne egymás után megtennĂĽnk. Ez persze nem egy hosszĂş távon működĹ‘kĂ©pes hozzáállás.
SegĂtsĂ©gĂĽnkre vannak ilyen helyzetekben a Prefab-ok. Egy-egy GameObject-bĹ‘l asset fájlt kĂ©szĂthetĂĽnk annak minden beállĂtásával, gyerek objektumával Ă©s a gyerek objektumok beállĂtásaival egyĂĽtt. Ezek a prefabok.
A prefab egy file, ami egy GameObject-et reprezentál gyerekeivel, komponenseivel Ă©s beállĂtásaival egyĂĽtt.
A prefabok lehetĹ‘vĂ© teszik a fejlesztĹ‘k számára a játĂ©k elemeinek elĹ‘re elkĂ©szĂtett, ĂşjrahasznosĂthatĂł változatainak lĂ©trehozását Ă©s használatát.
Prefab lĂ©trehozása Ă©s pĂ©ldányosĂtása
Prefab-ot úgy hozhatunk létre egy már létező GameObject-ből, hogy a Hierarchy ablakból Drag and Drop módszerrel áthúzzuk azt az Asset-ek közé a Project ablakra.
Ezután ha a filet bárhova visszahĂşzzuk a Scene-be, ott a prefab egy pĂ©ldánya fog szerepelni. Amikor egy scene-ben egy Prefab pĂ©ldány van jelen, akkor annak beállĂtásai nem a Scene rĂ©szei többĂ©.
Ha egy Prefab-ból példányt hozunk létre, akkor nem másoljuk a GameObject adatait a Scene-be, csak a referenciát az adott Prefab-ra. Az adatokat a Prefab-ról tehát maga a Prefab file tárolja nem a Scene. Egy Scene-ben csak a referencia szerepel a prefab file-ra.
Így, ha bármi változik a Prefab fájlbon, akkor minden Scene-beli példány módosulni fog vele együtt egyszerre és egységesen.
Egyedi mĂłdosĂtások: Overrides
Ha egy Scene béli prefab példányon változtatásokat hajtunk végre, akkor azok a változtatások nem fognak megjelenni automatikusan minden egyéb példányán is a Prefab-nak.
Ennek az az oka, hogy ezek a változtatások nem lesznek egybĹ‘l a prefab rĂ©szei, hanem csak az adott prefab pĂ©ldányhoz társĂtott mĂłdosĂtások maradnak, amik a Scene-en belĂĽl tárolĂłdnak el.
NĂ©zzĂĽk a korábbi pĂ©ldát az ellenfelekkel. Az a bizonyos gyakori ellenfĂ©l legyen pĂ©ldául egy kobold. Ha a kobold Prefab-on mĂłdosĂtjuk annak egy beállĂtását, teszem azt az ugrása magasságát állĂtjuk nagyobbra, akkor minden egyes kobold a játĂ©kban nagyobbat fog tudni ugrani.
Ezzel szemben, ha egyetlen kobold pĂ©ldány beállitását mĂłdosĂtjuk, akkor csak az az egy fog változni.
Egy prefab pĂ©ldányt tehát az eredeti prefab file Ă©s a Scene-ben lĂ©vĹ‘ egyedi mĂłdosĂtások Ărnak le.
Ezeket az egyedi felĂĽlĂrásokat override-nak nevezzĂĽk.
Azt, hogy egy prefab pĂ©ldány melyik beállĂtása jön az eredeti Prefab fájlbĂłl Ă©s melyik egyedi Scene-ben tárolt felĂĽlĂrás, azt a következĹ‘ mĂłdokon tudjuk megnĂ©zni:
- Inspector ablak
A prefab pĂ©ldányon a mĂłdosĂtott beállĂtások vastaggal szedve jelennek meg az Inspector ablakban.
Emellett ezen beállĂtások neve mellett bal oldalt egy kis kĂ©k fĂĽggĹ‘leges vonal jelenik meg.
Ugyanez a kis kĂ©k vonalka jelenik meg a Hierarchy ablakban is azon Prefab-ok esetĂ©ben, amik bármi egyedi mĂłdosĂtást tartalmaznak.
A (bal) fenti pĂ©ldában a Car prefab pĂ©ldány tartalmaz egyedi mĂłdosĂtásokat de a Car2 nem.
A Car pĂ©ldányon (fent jobbra) felĂĽl van Ărva a Rigidbody komponensen a Mass Ă©s a Constrains, a BoxCollider-en meg a Size beállĂtás, annak is csak a Z Ă©rtĂ©ke.
- Override menĂĽ
A prefab pĂ©ldányoknak megjelenik egy extra sor a GameObject Insperctor fejlĂ©cĂ©ben a Tag Ă©s a Layer alatt. Az Open gomb megnyitja a Prefab mĂłdĂş szerkesztĂ©st (kĂ©sĹ‘bb), a Select gomb kijelöli a pĂ©ldányhoz tartozĂł Prefab filet, az Override gomb alatt pedig ha megnyomtuk, kinyĂlik egy menĂĽ, amiben fel van sorolva az összes olyan komponens amin változtatások törtĂ©ntek. Egy komponenst kiválasztva megtekinthetĹ‘, az összes kĂĽlönbsĂ©g az eredeti prefab fájl Ă©s a egyedi változtatott verziĂłk közt.
Egy Prefab pĂ©ldányon-on mĂłdosĂthatĂł minden beállĂtás egyedileg, beleĂ©rtve a SerializeField-eket a saját MonoBehaviour szkripteken. Teljesen Ăşj komponenst is adhatunk egy GameObject-hez vagy törölhetjĂĽk is Ĺ‘ket egy Prefab pĂ©ldányon belĂĽl Ăşgy hogy a mĂłdosĂtás csak Override marad. Ki Ă©s bekapcsolhatunk gyerek GameObjcteket, sĹ‘t hozzá is adhatunk teljesen Ăşjakat, egyedĂĽl törölni nem tudunk GameObject-et, mint egyedi Prefab mĂłdosĂtás.
Apply és Revert
Egyedi mĂłdosĂtásokon kĂ©t fontos műveletet tudunk elvĂ©gezni:
- Revert: A mĂłdosĂtás visszavonása az adott prefab pĂ©ldányra
- Apply: A módostás alkalmazása a Prefab file-ra
Az eygedi mĂłdosĂtás (override) megszűnik Ă©s a pĂ©ldány ezután a prefab fájlban szereplĹ‘ beállĂtást fogja használni.
A mĂłdosĂtás ettĹ‘l fogva nem a pĂ©ldányra vett egyedi override a Scene-ben, hanem a prefab file rĂ©sze Ă©s igaz lesz az összes többi prefabra is.
MindkĂ©t műveletet elĂ©rjĂĽk egyszerűen a változtatott beállĂtás jobb egĂ©rgombbal elĹ‘hĂvhatĂł menĂĽjĂ©ben.
A változtatások csoportosan is alkalmazhatók vagy visszavonhatók az Overrides menüben a Revert All, Apply All gombokkal.
Egy mĂłdosĂtást csak akkor nem tudunk Apply-olni, ha az egy referencia egy GameObject-re vagy komponesre a Scene-en belĂĽl. Ez azĂ©rt van Ăgy mert Prefab file nem tartalmazhat referenciát egy Unity Object-re saját magán kĂvĂĽl.
A prefab mĂłd
Az egyik mĂłdja a Prefab-okon valĂł munkának, hogy egy Prefab-on egyedileg mĂłdosĂtjuk a beállĂtásokat Ă©s utána azt alkalmazzuk a Prefab fájlra, a mĂłdosĂtás ezáltal megtörĂ©nik minden pĂ©ldányon.
MásfelĹ‘l ha biztosan nem egyedi változást akarunk vĂ©grehajtani, akkor nem kell pĂ©ldányon dolgoznunk, hanem egybĹ‘l mĂłdosĂthatjuk a Prefab fájlt magát. Ehhez be kell lĂ©pnĂĽnk prefab mĂłdba. Ez alapvetĹ‘en kĂ©tfĂ©lekĂ©pp Ă©rhetĹ‘ el.
- A prefab fájlon keresztül
- Duplán a fájlra rákattintva.
- Egy prefab példányon keresztül
- A hierarch ablakban a pĂ©ldány melletti jobbra mutatĂł aprĂł nyĂlra kattintva.
- A prefab fájl Inspector ablakának fejlécében a Select gombra kattintva.
A második mód kicsivel eltér az elsőtől. Utóbbi esetben egy konkrét Prefab példányon dolgozunk. Ekkor az adott példány látszik a Scene ablakban annak környezetében, minden egyéb objektum azonban csak kifakulva látszik körülötte.
MindkĂ©t esetben a prefab mĂłdban törtĂ©nt mĂłdosĂtások a Prefab fájlba mentĹ‘dnek, tehát egybĹ‘l alkalmazva lesznek az összes pĂ©ldányra.
Nested Prefab
KĂ©pzeljĂĽnk el egy Ăşjabb pĂ©ldát! EzĂşttal is azokon a koboldokon dolgozunk, amik gyakran vannak jelen a játĂ©kban. Ezen koboldoknak van egy fegyverĂĽk is, ami szintĂ©n egy bonyolult objektum sok beállĂtással. A fegyver, egy nyĂlpuska Ă©s sok más helyen is feltűnik a játĂ©kban. A játĂ©kos karakter Ă©s más ellenfelek kezĂ©ben is lehet ugyanilyen nyĂlpuska. Fontos, hogy minden esetben a nyĂlpuska ugyanĂşgy működjön bárki kezĂ©ben is van. Ezáltal kis gyakorlás után a játĂ©kos ránĂ©zĂ©sre fogja tudni annak tulajdonságait, bárhol is találkozik vele a játĂ©kban.
Ebben az esetben a nyĂlpuskát is Ă©rdemes egy Prefab-kĂ©nt megalkotni Ă©s azt a kobold Prefab rĂ©szĂ©vĂ© tenni. Ezt nevezzĂĽk nested azaz beágyazott Prefab-nak: Mikor az egyik Prefab rĂ©sze egy referencia a másik Prefab-ra.
Ahogy a Scene sem tartalmazza a Prefab-hoz tartozó adatokat, mikor annak egy példánya van jelen a Scene-ben, úgy a Prefab sem tartalmazza az adatokat a belé ágyazott nested Prefab-ból, csak egy referenciát az adott (nested Prefab) fájl-ra.
Ebben az esetben, ha a nyĂlpuska Prefab-on változtatunk valamit, az meg fog törtĂ©nni minden egyes kobold pĂ©ldányon, de minden egyĂ©b helyen is, ahol a fegyver jelen va.
E módon bárhány szintbe rendezhetők a nested Prefab-ok (Prefab-ba ágyazott Prefab-ba ágyazott Prefab…). A gyakorlatban ritka, hogy ez 2-3 szint fölé nőjön.
TegyĂĽk fel, hogy egy olyan Prefab pĂ©ldánya van jelen egy Scene-ben, aminek magának is van beágyazott Prefab-ja, Ă©s egy egyedi mĂłdosĂtást hajtunk vĂ©gre ezen a Scene beli pĂ©ldányon, annak is a beágyazott Prefab rĂ©szĂ©n.
Ha az elĹ‘zĹ‘ pĂ©ldát visszĂĽk tovább, akkor teszem azt a nyĂlpuska lövĂ©si sebessĂ©gĂ©t állĂtjuk nagyobbra az egyik Scene-ben lĂ©vĹ‘ kobold pĂ©ldányon. Ebben az esetben a változtatás a megszokott mĂłdon egyedi lesz arra az egy ellenfĂ©l pĂ©ldányra. Sema többi hasonlĂł fegyver, sem a többi hasonlĂł kobold nem fog más sebessĂ©ggel lĹ‘ni, csak az az egy. A változtatás a Scene rĂ©szĂ©t kĂ©pezĹ‘ egyedi override lesz csak.
A változást a hagyományos módon vissza lehet vonni a Revert paranccsal, de ha alkalmazni vagy más néven Apply-olni szeretnénk, akkor már két lehetőségünk van:
- Alkalmazhatjuk a változást a külső Prefab-ra (példában kobold Prefab-ra).
- Alkalmazhatjuk a változást a nested Prefab-ra (pĂ©ldában nyĂlpuska Prefab-ra).
Az elsĹ‘ esetben a változás továbbra is egy override lesz, de nem a Scene-ben, hanem a kĂĽlsĹ‘ Prefab-ban. Ekkor minden kobold gyorsabban fog lĹ‘ni, de ha a játtĂ©kban máshol fordul elĹ‘ a nyĂlpuska, az nem kapja meg ezt az egyedi változást.
A második esetben ha a változást egĂ©szen a nested Prefab-ra hajtjuk vĂ©gre, akkor már minden játĂ©k beli nyĂlpuska máshogy fog működni, nem csak a koboldokĂ©.
Prefab Variant
A koboldokrĂłl tudnivalĂł, hogy a zöldek nyĂlpuskát használnak, a pirosak kardot, a szĂĽrkĂ©k, pedig buzogányt. Habár vannak tulajdonságok, amikben eltĂ©rnek, a kĂĽlönbözĹ‘ szĂnű koboldok a legtöbb szempontbĂłl hasonlĂłak. Ugyanakkorát ugranak, ugyanannyi Ă©letĂĽk van, ugyanolyan gyorsan futnak, ugyanaz a Mesh Ărja le az alakjukat Ă©s az animáciĂłjuk nagy rĂ©sze is megegyezik. EgyedĂĽl a fegyverĂĽk Ă©s a szĂnĂĽk (más material) kĂĽlönbözik.
Ebben az esetben az új piros és szürke koboldjaik nem teljesen új entitások, csak változatai vagy más szóval variánsai az eredeti kobold prefab-nak.
A prefab variáns egy olyan elĹ‘re elkĂ©szĂtett, ĂşjrahasznosĂthatĂł változata egy másik Unity prefab-nak, amely többnyire ugyanazokat az alapokat használja mint az eredeti, de bizonyos tulajdonságai felĂĽlĂrtak.
A prefab variánsok lehetővé teszik a játékfejlesztők számára, hogy különböző változatokat hozzanak létre egy prefab-ból amellett, hogy megőrzik az eredeti GameObject tulajdonságainak és belső szerkezetének nagy részét.
Egy prefab fájlbĂłl variánst Ăşgy hozhatunk lĂ©tre, hogy a Project ablakon jobb egĂ©rgombbal a filera kattintva elĹ‘hĂvjuk annak menĂĽjĂ©t Ă©s ott a “Create / Prefab Variant“ lehetĹ‘sĂ©get választjuk.
Ebben az esetben is a variánson végzett egyedi változtatásokat, más néven override-okat vissza tudjuk vonni a Revert paranccsal, valamint alkalmazni is az eredeti prefabra az Apply paranccsal.
Bármely szerializált informáciĂł felĂĽlĂrhatĂł egy variánson.
Prefab variánsok használata javĂthatja a fejlesztĂ©s folyamatának hatĂ©konyságát, Ă©s lehetĹ‘vĂ© teszi, hogy a játĂ©kfejlesztĹ‘k gyorsabban testre szabhassák a játĂ©kot a felhasználĂłk igĂ©nyeinek megfelelĹ‘en.
Unpack prefab
Ha egy Scene bĂ©li prefab pĂ©ldánybĂłl egy egyszerű, mezei GameObject-et szeretnĂ©nk kĂ©szĂteni, ami ugyen másolata az eredeti Prefab-nak, de többĂ© nincs kapcsolata a Prefab fájjllal, akkor azt az “Unpack Prefab” paranccsal tudjuk megteni.
Ezt a lehetőségeet Hierarchy ablakban a Prefab példányra kattintva jobb egérgombbal érjük el: Jobb kattintás a prefab példányon / Prefab / Unpack Prefab.
Ha itt az “Unpack Prefab Completely” lehetőséget választjuk akkor a beágyazott Prefab-ok referenciái is megszünnke.
Ezután semmi módositás a Prefab-on nem fog megtörténi ezen a GameObject-en, és forditva is semmilyen változtatás ezen a GameObject-en nem lesz alkalmazhetó az eredeti Prefab filera.
ArchitektĂşra prefabokkal
Ahogy a programozásban kiemelten fontos a kĂłdduplikálás elkerĂĽlĂ©se, Ăşgy projekt tervezĂ©snĂ©l ugyanakkora figyelmet kell fordĂtania arra, hogy az adatokat se duplikáljuk.
A Prefab-ok a legelemibb eszközeink közé tartoznak, ahhoz, hogy elkerüljük a redundanciát (vagyis az adatok többszörös tárolását) egy Unity projektben.
Ahogys redundáns kód úgy redundáns adat is hibás működéshez vezethet és ami még rosszabb, a hibát felismerni és megtalálni a gyakorlatban különösen nehéz tud lenni. Inkább javasolet minderre a tervezési fázisbanfigyelni.