scripting:tutorials:level2:tribute
Unterschiede
Hier werden die Unterschiede zwischen zwei Versionen der Seite angezeigt.
| Nächste Überarbeitung | Vorherige Überarbeitung | ||
| scripting:tutorials:level2:tribute [2023/11/08 15:30] – angelegt fritz_98 | scripting:tutorials:level2:tribute [2023/11/30 09:28] (aktuell) – fritz_98 | ||
|---|---|---|---|
| Zeile 6: | Zeile 6: | ||
| <code lua> | <code lua> | ||
| -- Komfortfunktion für das Bereitstellen von Tributen | -- Komfortfunktion für das Bereitstellen von Tributen | ||
| - | function AddTribute(_tribute) | + | function AddTribute(_Tribute) |
| - | assert(type(_tribute) == " | + | assert(type(_Tribute) == " |
| - | assert(type(_tribute.text) == " | + | assert(type(_Tribute.Text) == " |
| - | assert(type(_tribute.cost) == " | + | assert(type(_Tribute.Cost) == " |
| - | assert(type(_tribute.playerId) == " | + | assert(type(_Tribute.PlayerId) == " |
| - | assert(not _tribute.Tribute, "Tribut.Tribute darf nicht vorbelegt sein"); | + | |
| -- Hier wird eine globale Variable gesetzt, die außerhalb dieser Funktion nicht manipuliert werden sollte | -- Hier wird eine globale Variable gesetzt, die außerhalb dieser Funktion nicht manipuliert werden sollte | ||
| - | | + | |
| - | | + | |
| - | | + | |
| - | local tResCost | + | local CostTable |
| - | for k, v in pairs(_tribute.cost) do | + | for ResourceName, ResourceAmount |
| - | assert(ResourceType[k]); | + | assert(ResourceType[ResourceName], ResourceName .. " is not a valid resource" |
| - | assert(type(v) == " | + | assert((type(ResourceAmount) == " |
| - | table.insert(tResCost, ResourceType[k]); | + | table.insert(CostTable, ResourceType[ResourceName]) |
| - | table.insert(tResCost, v); | + | table.insert(CostTable, ResourceAmount) |
| end | end | ||
| - | Logic.AddTribute(_tribute.playerId, _tribute.Tribute, 0, 0, _tribute.text, unpack(tResCost)); | + | Logic.AddTribute(_Tribute.PlayerId, _Tribute.Tribute, 0, 0, _Tribute.Text, unpack(CostTable)) |
| - | SetupTributePaid(_tribute); | + | SetupTributePaid(_Tribute) |
| - | return | + | return |
| end | end | ||
| </ | </ | ||
| Die Tribut-Handhabung wird dadurch deutlich erleichtert. | Die Tribut-Handhabung wird dadurch deutlich erleichtert. | ||
| + | |||
| + | **Hinweis**: | ||
| ---- | ---- | ||
| Zeile 38: | Zeile 39: | ||
| ====Einfache Tribute erstellen==== | ====Einfache Tribute erstellen==== | ||
| - | Die oben gezeigte Funktion '' | + | Die oben gezeigte Funktion '' |
| ^Key^Value-Typ^Bedeutung^ | ^Key^Value-Typ^Bedeutung^ | ||
| - | |**playerId**|Player Id (Ganze Zahl 1-8)|Spieler-Id des Spielers, der den Tribut bezahlen kann| | + | |**PlayerId**|Player Id (Ganze Zahl 1-8)|Spieler-Id des Spielers, der den Tribut bezahlen kann| |
| - | |**text**|String|Text, | + | |**Text**|String|Text, |
| - | |**cost**|Table|Die Kosten des Tributs in einem [[ scripting: | + | |**Cost**|Table|Die Kosten des Tributs in einem [[ scripting: |
| |**Callback**|Funktion|Funktion, | |**Callback**|Funktion|Funktion, | ||
| - | **Wichtig**: | ||
| In einem einfachen Tribut-Beispiel soll Spieler 1 die Eisengrube eines Verbündeten für 500 Gold und 300 Holz erstehen können. Die Eisengrube existiert auf der Karte und hat den Skriptnamen ''" | In einem einfachen Tribut-Beispiel soll Spieler 1 die Eisengrube eines Verbündeten für 500 Gold und 300 Holz erstehen können. Die Eisengrube existiert auf der Karte und hat den Skriptnamen ''" | ||
| Zeile 52: | Zeile 52: | ||
| function CreateTributeBuyIronMine() | function CreateTributeBuyIronMine() | ||
| local Tribute = { | local Tribute = { | ||
| - | | + | |
| - | | + | |
| - | | + | |
| -- Die Namen der Ressourcen werden groß geschrieben | -- Die Namen der Ressourcen werden groß geschrieben | ||
| Gold = 500, | Gold = 500, | ||
| Zeile 71: | Zeile 71: | ||
| end | end | ||
| </ | </ | ||
| + | |||
| + | **Wichtig: | ||
| ---- | ---- | ||
| Zeile 77: | Zeile 79: | ||
| Die Verwendung einer Callback-Funktion erlaubt es dir, maximal flexibel auf die Entrichtung eines Tributs zu reagieren. Für einige Standardfälle gibt es allerdings vorgefertigte, | Die Verwendung einer Callback-Funktion erlaubt es dir, maximal flexibel auf die Entrichtung eines Tributs zu reagieren. Für einige Standardfälle gibt es allerdings vorgefertigte, | ||
| + | |||
| + | **Achtung**: | ||
| + | |||
| + | ^Key^Value-Typ^Bedeutung^ | ||
| + | | **Resources** | Table (assoziativ) | [[ scripting: | ||
| + | | **Technologies** | Table (Liste) | Liste der Technologien, | ||
| + | | **Entity** | String oder Zahl | Skriptname oder Entity-Id der Entity, die nach Bezahlung zum Spieler wechselt | | ||
| + | | **Entities** | String | Präfix eines Skriptnames, | ||
| + | | **Ralleypoint** | String oder Zahl | Skriptname oder Entity-Id der Entity, zu der die nach Bezahlung zum Spieler gewechselten Entities automatisch gehen (falls Siedler) | | ||
| + | | **Spawn** | Table (Liste) | Liste an Truppenbeschreibungen für Truppen, die nach der Bezahlung erscheinen sollen (siehe Einträge unterhalb) | | ||
| + | | **Spawn[i].Pos** | String oder Zahl | Für Truppenspawn: | ||
| + | | **Spawn[i].LeaderType** | Zahl (Leader Entity Type) | Für Truppenspawn: | ||
| + | | **Spawn[i].Soldiers** | Ganze Zahl | Für Truppenspawn: | ||
| + | | **Spawn[i].Ralleypoint** | String oder Zahl | Für Truppenspawn: | ||
| + | | **Spawn[i].AttackRalleypoint** | String oder Zahl | Für Truppenspawn: | ||
| + | |||
| + | **Hinweis**: | ||
| + | |||
| + | Für jeden dieser optionalen Parameter wollen wir ein kleines Beispiel und dessen Voraussetzungen geben. | ||
| + | |||
| + | ===Ressourcentausch=== | ||
| + | |||
| + | Ein Händler bietet einen Tribut zum Tausch einer Ressource gegen eine andere an: | ||
| + | <code lua> | ||
| + | function CreateTributeBuyIron() | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | Text = "Für 500 Holz erhaltet Ihr 300 Eisen", | ||
| + | Cost = { | ||
| + | Wood = 500 | ||
| + | }, | ||
| + | Resources = { | ||
| + | -- Achtung! Die Keys der erhaltenen Ressourcen werden klein geschrieben! | ||
| + | iron = 300 | ||
| + | } | ||
| + | } | ||
| + | |||
| + | AddTribute(Tribute) | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | ===Technologien per Tribut=== | ||
| + | |||
| + | Ein Dieb bietet an, die Technologie " | ||
| + | <code lua> | ||
| + | function CreateTributeBuySabotage() | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | Text = "Für 700 Taler und 400 Schwefel erhaltet Ihr die Technologie ' | ||
| + | Cost = { | ||
| + | Gold = 700, | ||
| + | Sulfur = 400 | ||
| + | }, | ||
| + | Technologies = { Technologies.T_ThiefSabotage } | ||
| + | } | ||
| + | |||
| + | AddTribute(Tribute) | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | ===Einzelne Entities kaufen=== | ||
| + | |||
| + | Wie das Beispiel von ganz oben: Der Spieler kann eine Eisengrube erstehen. Sie hat den Skriptnamen ''" | ||
| + | |||
| + | <code lua> | ||
| + | function CreateTributeBuyIronMine() | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | Text = "Für 500 Taler und 300 Holz erhaltet Ihr die Eisenmine Eures Verbündeten", | ||
| + | Cost = { | ||
| + | Gold = 500, | ||
| + | Wood = 300 | ||
| + | }, | ||
| + | Entity = " | ||
| + | } | ||
| + | | ||
| + | AddTribute(Tribute) | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | ===Mehrere Entities kaufen=== | ||
| + | |||
| + | Dario kauft sich zu Beginn einer Partie einige Leibeigene. Für das folgende Beispiel müssen auf der Karte eine Entity mit dem Skriptnamen ''" | ||
| + | |||
| + | <code lua> | ||
| + | function CreateTributeBuySerfs() | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | Text = "Für 200 Taler erhaltet Ihr einige Leibeigene", | ||
| + | Cost = { | ||
| + | Gold = 200, | ||
| + | }, | ||
| + | -- Alle Entities mit dem Namen " | ||
| + | Entities = " | ||
| + | -- ...und laufen nach dem Kauf zu Dario | ||
| + | Ralleypoint = " | ||
| + | } | ||
| + | | ||
| + | AddTribute(Tribute) | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | ===Truppen kaufen=== | ||
| + | |||
| + | Dario holt sich bei einem befreundeten Dorf Verstärkung. Damit die Truppen eine Position zum Spawnen haben, sollte eine '' | ||
| + | |||
| + | <code lua> | ||
| + | function CreateTributeBuyTroops() | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | Text = "Für 800 Taler, 400 Holz und 200 Eisen erhaltet Ihr vom Nachbardorf einige Truppen zur Unterstützung", | ||
| + | Cost = { | ||
| + | Gold = 800, | ||
| + | Wood = 400, | ||
| + | Iron = 200 | ||
| + | }, | ||
| + | -- Das Table Spawn ist eine Liste, in der die zu spawnenden Truppen nacheinander beschrieben sind | ||
| + | Spawn = { | ||
| + | -- Gespawnt werden: | ||
| + | -- 1 Trupp Kurzschwertkämpfer | ||
| + | { Pos = " | ||
| + | -- 2 Truppen Kurzbogenschützen | ||
| + | { Pos = " | ||
| + | { Pos = " | ||
| + | -- und 1 Trupp schwerer Reiter | ||
| + | { Pos = " | ||
| + | } | ||
| + | } | ||
| + | | ||
| + | AddTribute(Tribute) | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | ---- | ||
| ====Tribute entfernen==== | ====Tribute entfernen==== | ||
| + | |||
| + | Um Tribute wieder zu entfernen, wird die Funktion '' | ||
| + | |||
| + | <code lua> | ||
| + | function CreateTributeBuyIronMine() | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | Text = "Für 500 Taler und 300 Holz erhaltet Ihr die Eisenmine Eures Verbündeten", | ||
| + | Cost = { | ||
| + | Gold = 500, | ||
| + | Wood = 300 | ||
| + | }, | ||
| + | Callback = CallbackTributeBuyIronMine | ||
| + | } | ||
| + | | ||
| + | return Tribute.PlayerId, | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | bekommst du die Spieler-Id und die Tribut-Id beim Aufruf zurück: | ||
| + | |||
| + | <code lua> | ||
| + | TributeBuyIronMinePlayerId, | ||
| + | </ | ||
| + | |||
| + | Danach kannst du mit diesen beiden Variablen den Tribut wieder entfernen: | ||
| + | |||
| + | <code lua> | ||
| + | Logic.RemoveTribute(TributeBuyIronMinePlayerId, | ||
| + | </ | ||
| + | |||
| + | ---- | ||
| ====Zusätzliche Parameter==== | ====Zusätzliche Parameter==== | ||
| + | |||
| + | Du kannst dem '' | ||
| + | |||
| + | Auf diese Weise lässt sich zum Beispiel eine Schwierigkeitswahl definieren: | ||
| + | <code lua> | ||
| + | function InitDifficultyChoice() | ||
| + | -- Wir geben den Schwierigkeitsgraden Namen, um sie später im Skript leichter identifizieren zu können | ||
| + | DifficultyModes = { | ||
| + | Easy = 1, | ||
| + | Normal = 2, | ||
| + | Hard = 3, | ||
| + | VeryHard = 4 | ||
| + | } | ||
| + | | ||
| + | -- Jeder Schwierigkeitsgrad soll im Tribut als Name angezeigt werden können. Da diese Namen nur für die | ||
| + | -- Tribute gebraucht werden und nicht global identifizierbar sein müssen, genügt es, dieses Table lokal | ||
| + | -- zu definieren | ||
| + | local DifficultyModeNames = { | ||
| + | [DifficultyModes.Easy] = " | ||
| + | [DifficultyModes.Normal] = " | ||
| + | [DifficultyModes.Hard] = " | ||
| + | [DifficultyModes.VeryHard] = "Sehr Schwer" | ||
| + | } | ||
| + | | ||
| + | -- Eine globale Variable soll später den gewählten Schwierigkeitsgrad ausdrücken, | ||
| + | -- hier zurück | ||
| + | -- 0 ist laut unserem DifficultyModes-Table noch kein gültiger Schwierigkeitsgrad | ||
| + | Difficulty = 0 | ||
| + | | ||
| + | -- Es soll nur einer der angebotenen Schwierigkeitsgrade ausgewählt werden können | ||
| + | -- Wir speichern deshalb alle Tribute-Ids in einem Table zwischen | ||
| + | -- Später werden alle Tribute außer der gewählte wieder entfernt | ||
| + | DifficultyTributeIds = {} | ||
| + | -- Für jeden Schwierigkeitsgrad soll ein Tribut angelegt werden... | ||
| + | for DifficultyMode, | ||
| + | -- ...also brauchen wir die Zahl, die ihn ausdrückt und seinen Namen, den wir im lokalen | ||
| + | -- Table festgehalten haben | ||
| + | local TributeId = CreateTributeDifficultyChoice(DifficultyMode, | ||
| + | -- Die Funktion CreateTributeDifficultyChoice gibt die Tribut-Id zurück, die wir im globalen | ||
| + | -- Table DifficultyTributeIds speichern | ||
| + | table.insert(DifficultyTributeIds, | ||
| + | end | ||
| + | end | ||
| + | |||
| + | -- Es reicht eine Funktion für alle Schwierigkeitsgrade | ||
| + | -- Für jeden Schwierigkeitsgrad muss nur der Zahlenwert und der Name angegeben werden | ||
| + | function CreateTributeDifficultyChoice(_DifficultyMode, | ||
| + | local Tribute = { | ||
| + | PlayerId = 1, | ||
| + | -- Der Text benutzt einen der Parameter | ||
| + | Text = " | ||
| + | -- Die Wahl eines Schwierigkeitsgrades darf nichts kosten, deshalb setzen wir die Kosten | ||
| + | -- einer beliebigen Ressource auf 0 | ||
| + | Cost = { | ||
| + | Gold = 0 | ||
| + | }, | ||
| + | -- Hier speichern wir den Schwierigkeitsgrad, | ||
| + | -- Im Callback können wir auf ihn zugreifen | ||
| + | DifficultyMode = _DifficultyMode, | ||
| + | Callback = CallbackTributeDifficultyChoice | ||
| + | } | ||
| + | |||
| + | -- Die Tribut-Id muss zurückgegeben werden, damit später alle Schwierigkeitsgradtribute wieder | ||
| + | -- entfernt werden können, sobald einer davon ausgewählt wurde | ||
| + | return AddTribute(Tribute) | ||
| + | end | ||
| + | |||
| + | function CallbackTributeDifficultyChoice(_Tribute) | ||
| + | -- Innerhalb dieser Funktion haben wir Zugriff auf das Table _Tribute, in dem alle Informationen, | ||
| + | -- die wir zur Definition des Tributs definiert haben, gespeichert sind | ||
| + | -- _Tribute.DifficultyMode enthält deshalb den gewählten Schwierigkeitsgrad: | ||
| + | Difficulty = _Tribute.DifficultyMode | ||
| + | | ||
| + | -- _Tribute.Tribute enhält außerdem die Tribut-Id des Tributs. Damit und dem DifficultyTributeIds-Table | ||
| + | -- können wir die anderen Schwierigkeitstribute wieder entfernen | ||
| + | for _, TributeId in ipairs(DifficultyTributeIds) do | ||
| + | -- Lösche alle Tribute in DifficultyTributeIds, | ||
| + | if TributeId ~= _Tribute.Tribute then | ||
| + | -- Alle Tribute waren für Spieler 1 | ||
| + | Logic.RemoveTribute(_Tribute.PlayerId, | ||
| + | end | ||
| + | end | ||
| + | | ||
| + | -- Hiernach sollte dann der Questablauf starten | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | Später kann dann anhand der globalen Variable '' | ||
| + | |||
| + | <code lua> | ||
| + | function SpawnEnemyHorsemen() | ||
| + | local NumberOfTroops = 0 | ||
| + | if Difficulty == DifficultyModes.Easy then | ||
| + | NumberOfTroops = 3 | ||
| + | elseif Difficulty == DifficultyModes.Normal then | ||
| + | NumberOfTroops = 5 | ||
| + | elseif Difficulty == DifficultyModes.Hard then | ||
| + | NumberOfTroops = 6 | ||
| + | elseif Difficulty == DifficultyModes.VeryHard then | ||
| + | NumberOfTroops = 8 | ||
| + | end | ||
| + | | ||
| + | for i = 1, NumberOfTroops do | ||
| + | CreateMilitaryGroup(2, | ||
| + | end | ||
| + | end | ||
| + | </ | ||
| + | |||
| + | ---- | ||
| + | |||
| + | Im nächsten Kapitel wird gezeigt, wie sich das Auftragsmenü füllen und verwalten lässt. | ||
| + | |||
| + | [[ scripting: | ||
| + | [[ scripting: | ||
| + | [[ scripting: | ||
scripting/tutorials/level2/tribute.1699457416.txt.gz · Zuletzt geändert: 2023/11/08 15:30 von fritz_98
