Read this manual in English

Podstawowe elementy do budowania aplikacji

W samym sercu koncepcji silnika Defold znajduje się kilka elementów, których zrozumienie ułatwia dalszą pracę z silnikiem. Instrukcja ta wyjaśnia czym są takie bloki służące do budowania aplikacji. Po zapoznaniu się z poniższą instrukcją, warto przejść do Instrukcji adresowania i przesyłania wiadomości. Na stronie Defold znajdziesz również tutoriale dla początkujących dostępne nawet z poziomu edytora, aby umożliwić Ci szybki start z silnikiem Defold.

Building blocks

Przy budowaniu gier na silniku Defold używa się trzech podstawowych elementów:

Kolekcja (Collection)
Kolekcja jest plikiem używanym do stworzenia struktury Twojej gry. W kolekcjach buduje się hierarchię obiektów gry (poniżej) i innych kolekcji. Kolekcja jest więc po prostu zbiorem obiektów i innych kolekcji. Zazwyczaj używa się ich do stworzenia struktury całych poziomów w grach czy też grup wrogów, postaci, pocisków czy innych elementów (wielu obiektów).
Obiekt gry (Game object)
Obiekty gry są pojemnikami zawierającymi identyfikator (id), pozycję, orientację i skalę oraz mogą zawierać dodatkowo tzw. komponenty (poniżej). Są używane zazwyczaj do tworzenia postaci gracza, innych pojedynczych elementów, lub systemów tworzenia zasad gry oraz jako elementy wczytujące i zwalniające dane poziomy.
Komponent (Component)
Komponenty to elementy, które są umieszczane wewnątrz obiektów, aby nadać im cechy zgodne z ich typem - reprezentację wizualną (sprite, model, particlefx), dźwiękową (sound) czy logiczną (script). Są zazwyczaj używane do stworzenia sprite’ów czy modeli postaci, dodawania skryptów do obiektów czy efektów dźwiękowych czy cząsteczkowych.

Kolekcje

Kolekcje mają strukturę drzewa, która przechowuje obiekty i inne kolekcje. Kolekcje są zawsze przechowywane w formie pliku.

Kiedy Defold startuje, wczytuje pojedynczą, główną kolekcję bootrstrapową określoną w pliku “game.project”. Kolekcja bootstrapowa jest często nazywana “main.collection” (i tak jest też domyślnie nazwana po otwarciu każdego nowego projektu), ale oczywiście możesz używać dowolnej nazwy.

Kolekcja może zawierać obiekty i inne kolekcje (przez referencję do pliku sub-kolekcji) zagnieżdżone na dowolną “głębokość”. Poniżej jest przykład kolekcji “main.collection”. Zawiera ona jeden obiekt gry (z id “can”)i jedną sub-kolekcję (z id “bean”). Sub-kolekcja ta zawiera z kolei obiekty “bean” i “shield”.

Collection

Zauważ, że sub-kolekcja z id “bean” jest przechowywana w osobnym pliku nazwanym “/main/bean.collection”, a kolekcja nadrzędna “main.collection” zawiera do tego pliku jedynie referencję:

Bean collection

Nie można zaadresować kolekcji samej w sobie, ponieważ nie istnieją obiekty w czasie rzeczywistym, które reprezentują kolekcje “main” czy “bean” - nie można więc wysłać wiadomości do kolekcji samej w sobie, a tylko do obiektów i komponentów. Jednak czasem chcesz wysłać wiadomość do obiektu z innej kolekcji niż kolekcja, w której nadawca się znajduje, więc dlatego określą się ścieżkę (ang. path) do takiego obiektu z uwzględnieniem id kolekcji (Szczegóły znajdziesz w Instrukcji adresowania):

-- file: can.script
-- get position of the "bean" game object in the "bean" collection
local pos = go.get_position("bean/bean")

Kolekcja dodawana do innej kolekcji jest zawsze referencją do pliku kolekcji:

Naciśnij Prawy-przycisk-myszki na kolekcji w panelu Outline i wybierz Add Collection File.

Obiekty gry

Obiekty gry to bardzo proste obiekty posiadające indywidualny czas życia w trakcie wykonywania programu. Posiadają pozycję, orientację i skalę, a parametry te mogą być manipulowane i animowane osobno w czasie działania programu.

-- animate X position of "can" game object
go.animate("can", "position.x", go.PLAYBACK_LOOP_PINGPONG, 100, go.EASING_LINEAR, 1.0)

Obiekty gry mogą być używane jako puste obiekty (jako znacznik pozycji (ang. waypoint, startpoint, checkpoint etc.)), ale najczęściej zawierają komponenty, takie jak sprite’y, dźwięki, skrypty, modele, fabryki, efekty cząsteczkowe i inne. Obiekty te są tworzone albo z poziomu edytora i umieszczane bezpośrednio w plikach kolekcji (statycznie) albo dynamicznie, w kodzie, dzięki fabrykom (ang. factory).

Obiekty gry są więc dodawane jako nowe obiekty zdefiniowane w pliku kolekcji lub również w pliku kolekcji, ale jako referencja do osobnego pliku z definicją obiektu gry:

Naciśnij Prawy-przycisk-myszki na kolekcji w panelu Outline i wybierz Add Game Object (dodasz definicję do kolekcji) or Add Game Object File (dodasz do kolekcji referencję do pliku z definicją obiektu).

Jest to jeszcze dogłębniej wytłumaczone poniżej.

Komponenty

Components are used to give specific expression and/or functionality to game objects. Components have to be contained inside game objects and are affected by the position, rotation and scale of the game object that contains the component:

Components

Many components have type specific properties that can be manipulated and there are component type specific functions available for interacting with them in runtime:

-- disable the can "body" sprite
msg.post("can#body", "disable")

-- play "hoohoo" sound on "bean" in 1 second
sound.play("bean#hoohoo", { delay = 1, gain = 0.5 } )

Components are either added in-place in a game object, or added to a game object as a reference to a component file:

Right-click the game object in the Outline view and select Add Component (add in-place) or Add Component File (add as file reference).

In most cases it makes most sense to create components in-place, but the following component types must be created in separate resource files before being added by reference to a game object:

  • Script
  • GUI
  • Particle FX
  • Tile Map

Odsyłamy do osobnej Instrukcji do komponentów, gdzie znajduje się lista wszystkich komponentów silnika Defold.

Obiekty dodawane bezpośrednio i z pliku

Kiedy tworzysz plik kolekcji, obiektu gry lub nawet komponentu (np. w panelu Assets), tak naprawdę tworzysz tylko szablon, prototyp (ang. blueprint, prototype). Tworzy to tylko i wyłącznie plik w strukturze Twojego projektu, natomiast nic nie jest dodawane do samej gry. Aby stworzyć instancję kolekcji, obiektu czy komponentu do gry, która bazuje na takim pliku-szablonie, dodać należy taką instancję w jednej z Twoich kolekcji.

W panelu Outline możesz zobaczyć na jakim pliku bazuje dana instancja, jeśli była ona stworzona z pliku, a nie bezpośrednio w panelu Outline właśnie. Przykładowo, kolekcja “main.collection” poniżej zawiera trzy instancje, które bazują na już utworzonych plikach:

  1. Sub-kolekcja “bean”.
  2. Komponent typu skrypt “bean” w obiekcie “bean” w sub-kolekcji “bean”.
  3. Komponent typu skrypt “can” w obiekcie “can”.

Instance

Korzyścią z używania szablonów/plików jest zdecydowanie możliwość stworzenia wielu instancji obiektu gry lub kolekcji i zmiana ich wszystkich naraz w jednym pliku:

GO instances

Przy zmianie pliku każda instancja utworzona z tego pliku zostaje natychmiastowo zaktualizowana:

GO instances updated

Hierarchia obiektów gry - relacja rodzic-dziecko

W pliku kolekcji możesz tworzyć hierarchie obiektów gry (game objects) w ten sposób, że jeden z obiektów jest dzieckiem innego obiektu - rodzica. Po prostu przeciągnij jeden z obiektów gry i upuść nad innym obiektem - zostanie on umieszczony w drzewku pod tym obiektem i stanie się jego dzieckiem:

Childing game objects

Relacja rodzic-dziecko jest dynamiczną relacją wpływającą na zmianę pozycji, orientacji i skali obu obiektów. Każda transformacja tych wartości zaaplikowana do obiektu rodzica zostanie następnie zaaplikowana do obiektu dziecka, aby ich wzajemna, względna pozycja/orientacja/skala pozostała taka sama, 1:1, zarówno w edytorze jak i w czasie działania programu:

Child transform

Z kolei wszystkie transformacje na obiekcie dziecku są wykonywane w układzie odniesienia rodzica. W edytorze Defold możesz wybrać, czy operacje na obiekcie dziecku są wykonywane w układzie lokalnym rodzica (local space) czy w głównym układzie odniesienia (world space) klikając Edit ▸ World Space (domyślnie ustawione) lub Edit ▸ Local Space.

Jest też możliwe zmienienie rodzica danego obiektu przez wysłanie do niego wiadomości set_parent.

local parent = go.get_id("bean")
msg.post("child_bean", "set_parent", { parent_id = parent })

Częstym błędem jest postrzeganie przypisania obiektu jako dziecka innego obiektu w kolekcji jako zmiana miejsca tego obiektu w hierarchii kolekcji. Są to jednak dwie osobne rzeczy. Relacje rodzic-dziecko dynamicznie zmieniają graf w panelu Outline, co pozwala wizualnie ją przedstawić. Jedyną rzeczą, która określa adres obiektu jest jej miejsce w hierarchii kolekcji. Adres jest statyczny podczas całego cyklu życia obiektu.


Did you spot an error or do you have a suggestion? Please let us know on GitHub!

GITHUB