Skip to content

Commit 5bbf586

Browse files
committed
feat(core): add tutorial 29 code
1 parent 3d4034b commit 5bbf586

10 files changed

Lines changed: 385 additions & 67 deletions

File tree

Assets/Scenes/SampleScene.unity

Lines changed: 266 additions & 19 deletions
Large diffs are not rendered by default.

Assets/Scripts/Managers/GameManager.cs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
using System.Collections;
22
using System.Collections.Generic;
3+
using System.Linq;
34
using UnityEngine;
45
using UnityEngine.AI;
56

@@ -33,6 +34,8 @@ private void Awake()
3334
DataHandler.LoadGameData();
3435
GetComponent<DayAndNightCycler>().enabled = gameGlobalParameters.enableDayAndNightCycle;
3536

37+
Globals.InitializeGameResources(gamePlayersParameters.players.Length);
38+
3639
Globals.NAV_MESH_SURFACE = GameObject.Find("Terrain").GetComponent<NavMeshSurface>();
3740
Globals.UpdateNavMeshSurface();
3841

@@ -69,6 +72,27 @@ private void Update()
6972
}
7073
}
7174

75+
#if UNITY_EDITOR
76+
private void OnGUI()
77+
{
78+
GUILayout.BeginArea(new Rect(0f, 40f, 100f, 100f));
79+
80+
int newMyPlayerId = GUILayout.SelectionGrid(
81+
gamePlayersParameters.myPlayerId,
82+
gamePlayersParameters.players.Select((p, i) => i.ToString()).ToArray(),
83+
gamePlayersParameters.players.Length
84+
);
85+
86+
GUILayout.EndArea();
87+
88+
if (newMyPlayerId != gamePlayersParameters.myPlayerId)
89+
{
90+
gamePlayersParameters.myPlayerId = newMyPlayerId;
91+
EventManager.TriggerEvent("SetPlayer", newMyPlayerId);
92+
}
93+
}
94+
#endif
95+
7296
private void OnEnable()
7397
{
7498
EventManager.AddListener("PauseGame", _OnPauseGame);

Assets/Scripts/ScriptableObjects/Skills/SkillData.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,9 @@ public void Trigger(GameObject source, GameObject target = null)
2929
{
3030
BoxCollider coll = source.GetComponent<BoxCollider>();
3131
Vector3 instantiationPosition = new Vector3(
32-
source.transform.position.x + coll.size.x * 1.2f,
32+
source.transform.position.x + coll.size.x,
3333
source.transform.position.y,
34-
source.transform.position.z - coll.size.z * 1.2f
34+
source.transform.position.z - coll.size.z
3535
);
3636
CharacterData d = (CharacterData) unitReference;
3737
UnitManager sourceUnitManager = source.GetComponent<UnitManager>();

Assets/Scripts/ScriptableObjects/Units/UnitData.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,8 @@ public class UnitData : ScriptableObject
2424
[Header("General Sounds")]
2525
public AudioClip onSelectSound;
2626

27-
public bool CanBuy()
27+
public bool CanBuy(int owner)
2828
{
29-
return Globals.CanBuy(cost);
29+
return Globals.CanBuy(owner, cost);
3030
}
3131
}

Assets/Scripts/Tools/Globals.cs

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,7 @@ public static class Globals
1717
public static int TREE_MASK = 1 << 13;
1818
public static int ROCK_MASK = 1 << 14;
1919

20-
public static Dictionary<InGameResource, GameResource> GAME_RESOURCES = new Dictionary<InGameResource, GameResource>()
21-
{
22-
{ InGameResource.Gold, new GameResource("Gold", 1000) },
23-
{ InGameResource.Wood, new GameResource("Wood", 1000) },
24-
{ InGameResource.Stone, new GameResource("Stone", 1000) }
25-
};
20+
public static Dictionary<InGameResource, GameResource>[] GAME_RESOURCES;
2621

2722
public static Dictionary<InGameResource, int> XP_CONVERSION_TO_RESOURCE = new Dictionary<InGameResource, int>()
2823
{
@@ -42,10 +37,26 @@ public static void UpdateNavMeshSurface()
4237
NAV_MESH_SURFACE.UpdateNavMesh(NAV_MESH_SURFACE.navMeshData);
4338
}
4439

40+
public static void InitializeGameResources(int nPlayers)
41+
{
42+
GAME_RESOURCES = new Dictionary<InGameResource, GameResource>[nPlayers];
43+
for (int i = 0; i < nPlayers; i++)
44+
GAME_RESOURCES[i] = new Dictionary<InGameResource, GameResource>()
45+
{
46+
{ InGameResource.Gold, new GameResource("Gold", 1000) },
47+
{ InGameResource.Wood, new GameResource("Wood", 1000) },
48+
{ InGameResource.Stone, new GameResource("Stone", 1000) }
49+
};
50+
}
51+
4552
public static bool CanBuy(List<ResourceValue> cost)
53+
{
54+
return CanBuy(GameManager.instance.gamePlayersParameters.myPlayerId, cost);
55+
}
56+
public static bool CanBuy(int playerId, List<ResourceValue> cost)
4657
{
4758
foreach (ResourceValue resource in cost)
48-
if (GAME_RESOURCES[resource.code].Amount < resource.amount)
59+
if (GAME_RESOURCES[playerId][resource.code].Amount < resource.amount)
4960
return false;
5061
return true;
5162
}

Assets/Scripts/Tools/Utils.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,4 +163,14 @@ public static string CapitalizeWords(string str)
163163
}
164164
return string.Join(" ", words);
165165
}
166+
167+
public static Color LightenColor(Color color, float factor)
168+
{
169+
return new Color(
170+
Mathf.Clamp01(color.r + factor),
171+
Mathf.Clamp01(color.g + factor),
172+
Mathf.Clamp01(color.b + factor),
173+
Mathf.Clamp01(color.a + factor)
174+
);
175+
}
166176
}

Assets/Scripts/UI/Minimap.cs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,14 +4,17 @@
44
[RequireComponent(typeof(RectTransform))]
55
public class Minimap : MonoBehaviour, IPointerDownHandler, IPointerUpHandler
66
{
7+
public RectTransform minimapContainerRectTransform;
78
public Vector2 terrainSize;
89
private Vector2 _uiSize;
910

11+
private Vector2 _offset;
1012
private Vector2 _lastPointerPosition;
1113
private bool _dragging = false;
1214

1315
private void Start()
1416
{
17+
_offset = minimapContainerRectTransform.anchoredPosition;
1518
_uiSize = GetComponent<RectTransform>().sizeDelta;
1619
_lastPointerPosition = Input.mousePosition;
1720
}
@@ -25,7 +28,7 @@ private void Update()
2528

2629
if (delta.magnitude > Mathf.Epsilon)
2730
{
28-
Vector2 uiPos = Input.mousePosition / GameManager.instance.canvasScaleFactor;
31+
Vector2 uiPos = (new Vector2(Input.mousePosition.x, Input.mousePosition.y) - _offset) / GameManager.instance.canvasScaleFactor;
2932
Vector3 realPos = new Vector3(
3033
uiPos.x / _uiSize.x * terrainSize.x,
3134
0f,

Assets/Scripts/UI/UIManager.cs

Lines changed: 47 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
public class UIManager : MonoBehaviour
88
{
99
private BuildingPlacer _buildingPlacer;
10+
private int _myPlayerId;
1011

1112
public Color validTextColor;
1213
public Color invalidTextColor;
@@ -66,6 +67,9 @@ public class UIManager : MonoBehaviour
6667
[Header("Main Menu Panel")]
6768
public GameObject mainMenuPanel;
6869

70+
[Header("Misc")]
71+
public Image playerIndicatorImage;
72+
6973
private void Awake()
7074
{
7175
_buildingPlacer = GetComponent<BuildingPlacer>();
@@ -95,18 +99,6 @@ private void Awake()
9599

96100
mainMenuPanel.SetActive(false);
97101

98-
// create texts for each in-game resource (gold, wood, stone...)
99-
_resourceTexts = new Dictionary<InGameResource, Text>();
100-
foreach (KeyValuePair<InGameResource, GameResource> pair in Globals.GAME_RESOURCES)
101-
{
102-
GameObject display = Instantiate(gameResourceDisplayPrefab);
103-
display.name = pair.Key.ToString();
104-
_resourceTexts[pair.Key] = display.transform.Find("Text").GetComponent<Text>();
105-
display.transform.Find("Icon").GetComponent<Image>().sprite = Resources.Load<Sprite>($"Textures/GameResources/{pair.Key}");
106-
_SetResourceText(pair.Key, pair.Value.Amount);
107-
display.transform.SetParent(resourcesUIParent, false);
108-
}
109-
110102
// create buttons for each building type
111103
_buildingButtons = new Dictionary<string, Button>();
112104
for (int i = 0; i < Globals.BUILDING_DATA.Length; i++)
@@ -128,10 +120,6 @@ private void Awake()
128120
_AddBuildingButtonListener(b, i);
129121
button.transform.SetParent(buildingMenu, false);
130122
_buildingButtons[data.code] = b;
131-
if (!Globals.BUILDING_DATA[i].CanBuy())
132-
{
133-
b.interactable = false;
134-
}
135123
button.GetComponent<BuildingButton>().Initialize(Globals.BUILDING_DATA[i]);
136124
}
137125

@@ -142,6 +130,30 @@ private void Awake()
142130
ToggleSelectionGroupButton(i, false);
143131
}
144132

133+
private void Start()
134+
{
135+
_myPlayerId = GameManager.instance.gamePlayersParameters.myPlayerId;
136+
137+
// set player indicator color to match my player color
138+
Color c = GameManager.instance.gamePlayersParameters.players[_myPlayerId].color;
139+
c = Utils.LightenColor(c, 0.2f);
140+
playerIndicatorImage.color = c;
141+
142+
// create texts for each in-game resource (gold, wood, stone...)
143+
_resourceTexts = new Dictionary<InGameResource, Text>();
144+
foreach (KeyValuePair<InGameResource, GameResource> pair in Globals.GAME_RESOURCES[_myPlayerId])
145+
{
146+
GameObject display = Instantiate(gameResourceDisplayPrefab);
147+
display.name = pair.Key.ToString();
148+
_resourceTexts[pair.Key] = display.transform.Find("Text").GetComponent<Text>();
149+
display.transform.Find("Icon").GetComponent<Image>().sprite = Resources.Load<Sprite>($"Textures/GameResources/{pair.Key}");
150+
_SetResourceText(pair.Key, pair.Value.Amount);
151+
display.transform.SetParent(resourcesUIParent, false);
152+
}
153+
154+
_CheckBuyLimits();
155+
}
156+
145157
private void OnEnable()
146158
{
147159
EventManager.AddListener("UpdateResourceTexts", _OnUpdateResourceTexts);
@@ -153,6 +165,7 @@ private void OnEnable()
153165
EventManager.AddListener("DeselectUnit", _OnDeselectUnit);
154166
EventManager.AddListener("PlaceBuildingOn", _OnPlaceBuildingOn);
155167
EventManager.AddListener("PlaceBuildingOff", _OnPlaceBuildingOff);
168+
EventManager.AddListener("SetPlayer", _OnSetPlayer);
156169
}
157170

158171
private void OnDisable()
@@ -166,6 +179,7 @@ private void OnDisable()
166179
EventManager.RemoveListener("DeselectUnit", _OnDeselectUnit);
167180
EventManager.RemoveListener("PlaceBuildingOn", _OnPlaceBuildingOn);
168181
EventManager.RemoveListener("PlaceBuildingOff", _OnPlaceBuildingOff);
182+
EventManager.RemoveListener("SetPlayer", _OnSetPlayer);
169183
}
170184

171185
public void ToggleSelectionGroupButton(int groupIndex, bool on)
@@ -275,7 +289,7 @@ private void _CheckBuyLimits()
275289
);
276290
Text txt = resourceDisplay.Find("Text").GetComponent<Text>();
277291
int resourceAmount = int.Parse(txt.text);
278-
if (Globals.GAME_RESOURCES[resourceCode].Amount < resourceAmount)
292+
if (Globals.GAME_RESOURCES[_myPlayerId][resourceCode].Amount < resourceAmount)
279293
txt.color = invalidTextColor;
280294
else
281295
txt.color = validTextColor;
@@ -300,7 +314,7 @@ private void _SetResourceText(InGameResource resource, int value)
300314

301315
private void _OnUpdateResourceTexts()
302316
{
303-
foreach (KeyValuePair<InGameResource, GameResource> pair in Globals.GAME_RESOURCES)
317+
foreach (KeyValuePair<InGameResource, GameResource> pair in Globals.GAME_RESOURCES[_myPlayerId])
304318
_SetResourceText(pair.Key, pair.Value.Amount);
305319

306320
_CheckBuyLimits();
@@ -341,7 +355,7 @@ private void _OnUpdatePlacedBuildingProduction(object data)
341355
private void _OnCheckBuildingButtons()
342356
{
343357
foreach (BuildingData data in Globals.BUILDING_DATA)
344-
_buildingButtons[data.code].interactable = data.CanBuy();
358+
_buildingButtons[data.code].interactable = data.CanBuy(_myPlayerId);
345359
}
346360

347361
private void _OnHoverBuildingButton(object data)
@@ -383,6 +397,17 @@ private void _OnPlaceBuildingOff()
383397
placedBuildingProductionRectTransform.gameObject.SetActive(false);
384398
}
385399

400+
private void _OnSetPlayer(object data)
401+
{
402+
int playerId = (int)data;
403+
_myPlayerId = playerId;
404+
Color c = GameManager.instance.gamePlayersParameters.players[_myPlayerId].color;
405+
c = Utils.LightenColor(c, 0.2f);
406+
playerIndicatorImage.color = c;
407+
_OnUpdateResourceTexts();
408+
_CheckBuyLimits();
409+
}
410+
386411
public void SetInfoPanel(UnitData data)
387412
{
388413
SetInfoPanel(data.unitName, data.description, data.cost);
@@ -405,10 +430,9 @@ public void SetInfoPanel(string title, string description, List<ResourceValue> r
405430
t = g.transform;
406431
t.Find("Text").GetComponent<Text>().text = resource.amount.ToString();
407432
t.Find("Icon").GetComponent<Image>().sprite = Resources.Load<Sprite>($"Textures/GameResources/{resource.code}");
408-
// check to see if resource requirement is not
409-
// currently met - in that case, turn the text into the "invalid"
410-
// color
411-
if (Globals.GAME_RESOURCES[resource.code].Amount < resource.amount)
433+
// check to see if resource requirement is not currently met -
434+
// in that case, turn the text into the "invalid" color
435+
if (Globals.GAME_RESOURCES[_myPlayerId][resource.code].Amount < resource.amount)
412436
t.Find("Text").GetComponent<Text>().color = invalidTextColor;
413437
t.SetParent(_infoPanelResourcesCostParent, false);
414438
}

Assets/Scripts/Units/BehaviorTree/BuildingBT.cs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,6 @@ protected override Node SetupTree()
3636
}
3737

3838
_root.Attach(new Sequence(new List<Node> {
39-
new CheckUnitIsMine(manager),
4039
new Timer(
4140
GameManager.instance.producingRate,
4241
new List<Node>()

Assets/Scripts/Units/Unit.cs

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -131,22 +131,20 @@ public virtual void Place()
131131
// for collisions with units
132132
_transform.GetComponent<BoxCollider>().isTrigger = false;
133133

134-
if (_owner == GameManager.instance.gamePlayersParameters.myPlayerId)
134+
// update game resources: remove the cost of the building
135+
// from each game resource
136+
foreach (ResourceValue resource in _data.cost)
135137
{
136-
_transform.GetComponent<UnitManager>().EnableFOV(_fieldOfView);
137-
138-
// update game resources: remove the cost of the building
139-
// from each game resource
140-
foreach (ResourceValue resource in _data.cost)
141-
{
142-
Globals.GAME_RESOURCES[resource.code].AddAmount(-resource.amount);
143-
}
138+
Globals.GAME_RESOURCES[_owner][resource.code].AddAmount(-resource.amount);
144139
}
140+
141+
if (_owner == GameManager.instance.gamePlayersParameters.myPlayerId)
142+
_transform.GetComponent<UnitManager>().EnableFOV(_fieldOfView);
145143
}
146144

147145
public bool CanBuy()
148146
{
149-
return _data.CanBuy();
147+
return _data.CanBuy(_owner);
150148
}
151149

152150
public void LevelUp()
@@ -169,7 +167,7 @@ public void LevelUp()
169167
// consume resources
170168
foreach (ResourceValue resource in _levelUpData.cost)
171169
{
172-
Globals.GAME_RESOURCES[resource.code].AddAmount(-resource.amount);
170+
Globals.GAME_RESOURCES[_owner][resource.code].AddAmount(-resource.amount);
173171
}
174172
EventManager.TriggerEvent("UpdateResourceTexts");
175173

@@ -186,7 +184,9 @@ public void LevelUp()
186184
public void ProduceResources()
187185
{
188186
foreach (KeyValuePair<InGameResource, int> resource in _production)
189-
Globals.GAME_RESOURCES[resource.Key].AddAmount(resource.Value);
187+
{
188+
Globals.GAME_RESOURCES[_owner][resource.Key].AddAmount(resource.Value);
189+
}
190190
}
191191

192192
public void TriggerSkill(int index, GameObject target = null)

0 commit comments

Comments
 (0)