Daten-Assets
Teil des Abschnitts Spielarchitektur in Unity der Unity-Journey von Coddy. Lektion 19 von 50.
In einem Farmspiel wachsen Karotten und Kürbisse. Eine Karotte wächst 30 Sekunden lang und wird für 5 Münzen verkauft, ein Kürbis wächst 90 Sekunden lang und wird für 40 verkauft. Diese Zahlen gehören zur Pflanze, nicht zu einer einzelnen Pflanze: Als Inspector-Felder in einem Plant-Skript hat jede Karotte in jeder Szene ihre eigene Kopie von 30 und 5, und bei einer Änderung müssen sie alle gefunden werden. Ein ScriptableObject speichert solche Daten in einem Asset, einer Datei im Projekt, auf die beliebig viele Objekte verweisen können. Seine Klasse leitet sich von ScriptableObject statt von MonoBehaviour ab:
using UnityEngine;
[CreateAssetMenu(fileName = "NewPlant", menuName = "Farm/Plant Data")]
public class PlantData : ScriptableObject
{
public string plantName;
public float growTime;
public int sellPrice;
}[CreateAssetMenu] fügt die Klasse dem Menü Create im Project-Fenster hinzu. Klicke im Project-Fenster mit der rechten Maustaste, wähle Create > Farm > Plant Data, und Unity erstellt ein Asset namens NewPlant; benenne es in Carrot um, wähle es aus und gib Carrot, 30 und 5 in die Felder im Inspector ein. Ein Pumpkin-Asset wird auf dieselbe Weise erstellt. Die Klasse kommt in eine nach ihr benannte Datei, PlantData.cs, wie auch bei einem MonoBehaviour.
Das Verhalten bleibt in einem MonoBehaviour mit einem Feld vom Typ des Assets. Ziehe das Carrot-Asset auf dieses Feld, und das Skript liest die Zahlen darüber aus:
public class Plant : MonoBehaviour
{
public PlantData data;
private float age;
void Update()
{
age += Time.deltaTime;
if (age >= data.growTime)
{
Debug.Log(data.plantName + " is ready, worth " + data.sellPrice);
enabled = false;
}
}
}Ein ScriptableObject befindet sich auf keinem GameObject und in keiner Szene. Es hat keinen Transform, und Unity ruft niemals sein Update oder Start auf: Es speichert Daten, und das Plant enthält das Verhalten. Wenn 200 Karotten auf dasselbe Carrot-Asset verweisen, ändert das Setzen von growTime auf 25 alle 200. Im Code wird eine Instanz mit ScriptableObject.CreateInstance<PlantData>() erstellt, niemals mit new.
Aufgabe
MittelDer Hero bewegt sich mit den Pfeiltasten durch die Arena. Name, Geschwindigkeit und Farbe sind Felder des Hero-Skripts, und jeder neue Hero müsste sie erneut kopieren. Verschiebe sie in ein Asset:
- Schreibe in
HeroData.csHeroData, ein ScriptableObject mit den öffentlichen FeldernheroName(ein String),moveSpeed(ein Float) undcolor(eine Color). Füge[CreateAssetMenu]mit dem MenünamenHeroes/Hero Datahinzu. - Ersetze in
Hero.csdie drei Felder durch ein öffentliches Felddatavom Typ HeroData und verwende die Werte des Assets dort, wo das Skript bisher seine eigenen Werte verwendet hat.
Das Projekt enthält ein mit diesem Menü erstelltes Knight-Asset (Knight, Geschwindigkeit 3, Rot), und der Inspector weist es dem Feld data des Hero zu. Drücke Play und bewege den Knight umher, dann klicke auf Check.
Probier es selbst
using UnityEngine;
// HeroData: Name, Geschwindigkeit und Farbe des Helden als ScriptableObject
Diese Lektion enthält ein kurzes Quiz. Starte die Lektion, um es zu beantworten und deinen Fortschritt zu speichern.
Alle Lektionen in Spielarchitektur in Unity
1Komponenten statt Hierarchien
Kleine KomponentenEin Basisskript für GegnerAbstrakte KomponentenKomponenten im ZusammenspielRückblick: Modularer Geschützturm4Serialisierte Daten
Serialisierbare KlassenListen im InspectorEnums im InspectorRückblick: Loot-Tabelle7Zustandsautomaten
Zustände als KlassenEin ZustandsautomatÜbergängeGegner-KIWiederholung: Türzustände10Projekt: Arena-Überlebenskampf
Der HeldGegnertypen2Interfaces in Unity
IDamageableInterfaces und TryGetComponentGetComponentsRückblick: Interaktionstaste5ScriptableObjects
Daten-AssetsWaffenwerteGemeinsame EinstellungenWellen als DatenRückblick: Item-Datenbank8Wiederverwendbarer Code
ErweiterungsmethodenEin generisches SingletonGenerische HilfsmethodenRückblick: FindNearest