Skip to content

Commit a78d399

Browse files
feat: Player 2 spine selection, fix: placeholder spine becomes default lamb, fix custom enemy spawn issue
1 parent ab8f6bc commit a78d399

6 files changed

Lines changed: 90 additions & 20 deletions

File tree

COTL_API/CustomEnemy/CustomEnemy.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,10 @@ public abstract class CustomEnemy
77
{
88
internal string ModPrefix = "";
99
public abstract string InternalName { get; }
10-
1110
public Enemy enemyType = Enemy.None;
12-
1311
public virtual string EnemyToMimic => "Assets/Prefabs/Enemies/All/Enemy Forest Archer Tennis.prefab";
14-
1512
public virtual SkeletonDataAsset? SpineOverride => null;
13+
public virtual CustomEnemyController? EnemyController => null; //setting this will disable the original AI and replace with this
14+
public virtual float maxHealth => 1f;
15+
1616
}

COTL_API/CustomEnemy/CustomEnemyManager.cs

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,6 @@ public static Enemy Add(CustomEnemy customEnemy)
2323

2424
CustomEnemyList.Add(innerType, customEnemy);
2525
LogWarning($"Added: {innerType} {customEnemy.InternalName} {customEnemy.ModPrefix}");
26-
27-
var enemyPrefab = BuildEnemyPrefab(customEnemy);
2826

2927
return innerType;
3028
}
@@ -54,19 +52,33 @@ public static IEnumerator BuildEnemyPrefab(CustomEnemy customEnemy)
5452

5553
public static UnitObject? Spawn(Enemy enemyType, Vector3 position)
5654
{
57-
//check if enemyType is in CustomEnemyPrefabList
5855
if (!CustomEnemyPrefabList.ContainsKey(enemyType))
5956
{
6057
LogWarning($"No custom enemy prefab found for {enemyType}!");
6158
return null;
6259
}
6360

6461
var prefab = CustomEnemyPrefabList[enemyType];
62+
var objInfo = CustomEnemyList[enemyType];
6563
var obj = UnityEngine.Object.Instantiate(prefab, position, Quaternion.identity);
6664
var unitObject = obj.GetComponent<UnitObject>();
6765

6866
if (unitObject != null)
6967
{
68+
unitObject.health.totalHP = objInfo.maxHealth;
69+
unitObject.health.HP = objInfo.maxHealth;
70+
71+
if (objInfo.SpineOverride != null)
72+
{
73+
//apply spine override here
74+
}
75+
76+
if (objInfo.EnemyController != null)
77+
{
78+
//apply enemy controller here, remove original controller
79+
}
80+
81+
7082
CustomSpawnedEnemies.Add(unitObject);
7183
return unitObject;
7284
}

COTL_API/CustomSkins/CustomSkinManager.cs

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ public static partial class CustomSkinManager
3434
internal static readonly Dictionary<string, SkeletonDataAsset?> CustomPlayerSpines = [];
3535
internal static readonly Dictionary<string, SkeletonDataAsset?> CustomFollowerSpines = [];
3636
internal static string SelectedSpine = "";
37+
internal static string SelectedSpine2 = "";
3738
internal static int NumGenericAtlases;
3839

3940
internal static readonly Dictionary<string, CustomPlayerSkin> CustomPlayerSkins = [];
@@ -553,15 +554,31 @@ public static void AddPlayerSpine(string name, SkeletonDataAsset? skeletonDataAs
553554

554555
if (Plugin.CustomPlayerSpineSettings != null)
555556
Plugin.CustomPlayerSpineSettings.Options = [.. CustomPlayerSpines.Keys];
557+
558+
if (Plugin.CustomPlayer2SpineSettings != null)
559+
Plugin.CustomPlayer2SpineSettings.Options = [.. CustomPlayerSpines.Keys];
556560
}
557561

558-
public static void ChangeSelectedPlayerSpine(string name)
562+
public static void ChangeSelectedPlayerSpine(string name, int playerId = 0)
559563
{
560564
// var splitted = name.Split(['/'], 2);
561565
if (!CustomPlayerSpines.ContainsKey(name) || CustomPlayerSpines[name] == null) return;
562-
SelectedSpine = name;
563566

564-
LogInfo($"Selected Spine: {SelectedSpine}");
567+
switch (playerId)
568+
{
569+
case 0:
570+
SelectedSpine = name;
571+
break;
572+
case 1:
573+
SelectedSpine2 = name;
574+
break;
575+
default:
576+
SelectedSpine = name;
577+
break;
578+
}
579+
580+
581+
LogInfo($"Selected Spine P1: {SelectedSpine} , P2: {SelectedSpine2}");
565582
}
566583

567584
public static void AddFollowerSpine(string name, SkeletonDataAsset? skeletonDataAsset)

COTL_API/CustomSkins/CustomSkinPatches.cs

Lines changed: 17 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -125,13 +125,15 @@ private static bool PlayerFarming_SetSkin(ref Skin __result, PlayerFarming __ins
125125

126126
SkinUtils.InvokeOnFindSkin(playerType);
127127

128-
if (!PlayerSkinOverride.ContainsKey(playerType) && !CustomPlayerSpines.ContainsKey(SelectedSpine)) return true;
128+
var spineOverride = (CoopManager.CoopActive && __instance.playerID == 1) ? SelectedSpine2 : SelectedSpine;
129+
130+
if (!PlayerSkinOverride.ContainsKey(playerType) && !CustomPlayerSpines.ContainsKey(spineOverride)) return true;
129131

130132
__instance.IsGoat = DataManager.Instance.PlayerVisualFleece == 1003;
131133
__instance.PlayerSkin = new Skin("Player Skin");
132134
List<Skin?>? skinToUse = null;
133135

134-
if (PlayerSkinOverride.ContainsKey(playerType) && !CustomPlayerSpines.ContainsKey(SelectedSpine))
136+
if (PlayerSkinOverride.ContainsKey(playerType) && !CustomPlayerSpines.ContainsKey(spineOverride))
135137
{
136138
skinToUse = PlayerSkinOverride[playerType];
137139
if (skinToUse == null) return true;
@@ -141,7 +143,7 @@ private static bool PlayerFarming_SetSkin(ref Skin __result, PlayerFarming __ins
141143
}
142144
else
143145
{
144-
var selectedSpineSkin = SelectedSpine.Split(['/'], 2)[1];
146+
var selectedSpineSkin = spineOverride.Split(['/'], 2)[1];
145147
__instance.PlayerSkin.AddSkin(__instance.Spine.Skeleton.Data.FindSkin(selectedSpineSkin));
146148
}
147149

@@ -231,15 +233,20 @@ private static bool PlayerFarming_BleatRoutine(PlayerFarming __instance)
231233
[HarmonyPrefix]
232234
private static bool PlayerFarming_Start(PlayerFarming __instance)
233235
{
234-
if (CustomPlayerSpines.Count == 0)
236+
// swap the placeholder with the default spine when player enters the game
237+
if (!CustomPlayerSpines.ContainsKey("Default"))
235238
AddPlayerSpine("Default", PlayerFarming.Instance.Spine.skeletonDataAsset, ["Lamb", "Goat", "Owl", "Snake"]);
236239

237-
if (SelectedSpine == "") return true;
238-
if (!CustomPlayerSpines.ContainsKey(SelectedSpine)) return true;
239-
if (CustomPlayerSpines[SelectedSpine] == null) return true;
240+
if (CustomPlayerSpines.ContainsKey("Placeholder"))
241+
CustomPlayerSpines.Remove("Placeholder");
242+
243+
var spineOverride = (CoopManager.CoopActive && __instance.playerID == 1) ? SelectedSpine2 : SelectedSpine;
244+
if (spineOverride == "") return true;
245+
if (!CustomPlayerSpines.ContainsKey(spineOverride)) return true;
246+
if (CustomPlayerSpines[spineOverride] == null) return true;
240247

241-
var selectedSpineSkin = SelectedSpine.Split(['/'], 2)[1];
242-
var runtimeSkeletonAsset = CustomPlayerSpines[SelectedSpine];
248+
var selectedSpineSkin = spineOverride.Split(['/'], 2)[1];
249+
var runtimeSkeletonAsset = CustomPlayerSpines[spineOverride];
243250
PlayerFarming.Instance.Spine.skeletonDataAsset = runtimeSkeletonAsset;
244251
PlayerFarming.Instance.Spine.initialSkinName = selectedSpineSkin;
245252
PlayerFarming.Instance.Spine.Initialize(true);
@@ -251,7 +258,7 @@ private static bool PlayerFarming_Start(PlayerFarming __instance)
251258
PlayerFarming.Instance.simpleSpineAnimator.anim.AnimationState.Event +=
252259
PlayerFarming.Instance.simpleSpineAnimator.SpineEventHandler;
253260

254-
LogInfo("Loaded Custom Spine " + SelectedSpine + " with skin " + selectedSpineSkin);
261+
LogInfo("Loaded Custom Spine " + spineOverride + " with skin " + selectedSpineSkin + " For player ID " + __instance.playerID);
255262

256263
return true;
257264
}

COTL_API/Debug/DebugEnemy.cs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
using System;
2+
3+
namespace COTL_API.Debug;
4+
5+
public class DebugEnemy : CustomEnemy.CustomEnemy
6+
{
7+
public override string InternalName => "DebugEnemy";
8+
}

COTL_API/Plugin.cs

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
using BepInEx;
33
using BepInEx.Configuration;
44
using BepInEx.Logging;
5+
using COTL_API.CustomEnemy;
56
using COTL_API.CustomInventory;
67
using COTL_API.CustomObjectives;
78
using COTL_API.CustomSettings;
@@ -27,6 +28,7 @@ public class Plugin : BaseUnityPlugin
2728
internal static Dropdown? GoatFleeceBleatSettings;
2829

2930
internal static Dropdown? CustomPlayerSpineSettings;
31+
internal static Dropdown? CustomPlayer2SpineSettings;
3032
internal readonly Harmony _harmony = new(MyPluginInfo.PLUGIN_GUID);
3133

3234
internal readonly ModdedSaveData<ApiData> APIData = new(MyPluginInfo.PLUGIN_GUID)
@@ -149,7 +151,16 @@ private void Awake()
149151
[.. CustomSkinManager.CustomPlayerSpines.Keys], i =>
150152
{
151153
CustomSkinManager.ChangeSelectedPlayerSpine(
152-
CustomSkinManager.CustomPlayerSpines.Keys.ElementAt(i));
154+
CustomSkinManager.CustomPlayerSpines.Keys.ElementAt(i), 0);
155+
});
156+
157+
CustomPlayer2SpineSettings = CustomSettingsManager.AddSavedDropdown("API", MyPluginInfo.PLUGIN_GUID,
158+
"Custom player 2 spine",
159+
"Lamb Spine",
160+
[.. CustomSkinManager.CustomPlayerSpines.Keys], i =>
161+
{
162+
CustomSkinManager.ChangeSelectedPlayerSpine(
163+
CustomSkinManager.CustomPlayerSpines.Keys.ElementAt(i), 1);
153164
});
154165

155166
CustomSettingsManager.AddBepInExConfig("API", "Skip splash screen", _skipSplashScreen);
@@ -226,6 +237,21 @@ public void Update()
226237
if (Input.GetKeyDown(KeyCode.F3))
227238
foreach (var x in PlayerFarming.Instance.Spine.Skeleton.Skin.Attachments)
228239
LogDebug($"{{ \"{x.Name}\", Tuple.Create({x.SlotIndex}, \"{x.Name}\") }}");
240+
241+
if (Input.GetKeyDown(KeyCode.F10))
242+
{
243+
var enemyPrefab = new DebugEnemy();
244+
var enemy = CustomEnemyManager.Add(enemyPrefab);
245+
StartCoroutine(CustomEnemyManager.BuildEnemyPrefab(enemyPrefab));
246+
LogInfo($"Generated Enemy Prefab: {enemyPrefab.EnemyToMimic}");
247+
248+
}
249+
if (Input.GetKeyDown(KeyCode.F11))
250+
{
251+
if (CustomEnemyManager.CustomEnemyList.Count < 0) return;
252+
CustomEnemyManager.Spawn(CustomEnemyManager.CustomEnemyList.Keys.ElementAt(0), PlayerFarming.Instance.transform.position);
253+
LogInfo($"Spawned debug enemy: {CustomEnemyManager.CustomEnemyList.Keys.ElementAt(0)}");
254+
}
229255
}
230256

231257
private void OnEnable()

0 commit comments

Comments
 (0)