about summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--AnodyneArchipelago/ArchipelagoManager.cs11
-rw-r--r--AnodyneArchipelago/ArchipelagoTreasure.cs22
-rw-r--r--AnodyneArchipelago/Locations.cs4
-rw-r--r--AnodyneArchipelago/Plugin.cs108
4 files changed, 141 insertions, 4 deletions
diff --git a/AnodyneArchipelago/ArchipelagoManager.cs b/AnodyneArchipelago/ArchipelagoManager.cs index 4ffa3af..4ceb68a 100644 --- a/AnodyneArchipelago/ArchipelagoManager.cs +++ b/AnodyneArchipelago/ArchipelagoManager.cs
@@ -131,7 +131,8 @@ namespace AnodyneArchipelago
131 131
132 string mapName = GetMapNameForDungeon(dungeonName); 132 string mapName = GetMapNameForDungeon(dungeonName);
133 GlobalState.inventory.AddMapKey(mapName, 1); 133 GlobalState.inventory.AddMapKey(mapName, 1);
134 } else if (itemName == "Green Key") 134 }
135 else if (itemName == "Green Key")
135 { 136 {
136 GlobalState.inventory.BigKeyStatus[0] = true; 137 GlobalState.inventory.BigKeyStatus[0] = true;
137 } 138 }
@@ -142,10 +143,16 @@ namespace AnodyneArchipelago
142 else if (itemName == "Red Key") 143 else if (itemName == "Red Key")
143 { 144 {
144 GlobalState.inventory.BigKeyStatus[1] = true; 145 GlobalState.inventory.BigKeyStatus[1] = true;
145 } else if (itemName == "Jump Shoes") 146 }
147 else if (itemName == "Jump Shoes")
146 { 148 {
147 GlobalState.inventory.CanJump = true; 149 GlobalState.inventory.CanJump = true;
148 } 150 }
151 else if (itemName == "Health Cicada")
152 {
153 GlobalState.MAX_HEALTH += 1;
154 GlobalState.CUR_HEALTH = GlobalState.MAX_HEALTH;
155 }
149 } 156 }
150 } 157 }
151} 158}
diff --git a/AnodyneArchipelago/ArchipelagoTreasure.cs b/AnodyneArchipelago/ArchipelagoTreasure.cs index 6d000e8..b3812f2 100644 --- a/AnodyneArchipelago/ArchipelagoTreasure.cs +++ b/AnodyneArchipelago/ArchipelagoTreasure.cs
@@ -1,4 +1,6 @@
1using AnodyneSharp.Entities.Gadget.Treasures; 1using AnodyneSharp.Entities;
2using AnodyneSharp.Entities.Gadget.Treasures;
3using AnodyneSharp.Registry;
2using Microsoft.Xna.Framework; 4using Microsoft.Xna.Framework;
3 5
4namespace AnodyneArchipelago 6namespace AnodyneArchipelago
@@ -14,7 +16,23 @@ namespace AnodyneArchipelago
14 16
15 public override void GetTreasure() 17 public override void GetTreasure()
16 { 18 {
17 base.GetTreasure(); 19 if (_location == "Street - Broom Chest")
20 {
21 BroomTreasure broomTreasure = new("broom-icon", this.Position, BroomType.Normal);
22 broomTreasure.GetTreasure();
23 GlobalState.SpawnEntity(broomTreasure);
24 }
25 else if (_location == "Street - Key Chest")
26 {
27 KeyTreasure keyTreasure = new(this.Position);
28 keyTreasure.GetTreasure();
29 GlobalState.SpawnEntity(keyTreasure);
30 }
31 else
32 {
33 base.GetTreasure();
34 }
35
18 ArchipelagoManager.SendLocation(_location); 36 ArchipelagoManager.SendLocation(_location);
19 } 37 }
20 } 38 }
diff --git a/AnodyneArchipelago/Locations.cs b/AnodyneArchipelago/Locations.cs index 46e2471..a1a54b2 100644 --- a/AnodyneArchipelago/Locations.cs +++ b/AnodyneArchipelago/Locations.cs
@@ -8,10 +8,14 @@ namespace AnodyneArchipelago
8 { 8 {
9 public static Dictionary<Guid, string> LocationsByGuid = new() 9 public static Dictionary<Guid, string> LocationsByGuid = new()
10 { 10 {
11 {new Guid("1525ead8-4d92-a815-873a-4dc04037d973"), "Street - Broom Chest" },
12 {new Guid("3307aa58-ccf1-fb0d-1450-5af0a0c458f7"), "Street - Key Chest" },
13 {new Guid("1bcddffb-5f98-4787-3a81-d1ce8fdeca29"), "Overworld - Near Gate Chest" },
11 {new Guid("40de36cf-9238-f8b0-7a57-c6c8ca465cc2"), "Temple of the Seeing One - Entrance Chest" }, 14 {new Guid("40de36cf-9238-f8b0-7a57-c6c8ca465cc2"), "Temple of the Seeing One - Entrance Chest" },
12 {new Guid("621c284f-cbd0-74c3-f51b-2a9fdde8d4d7"), "Temple of the Seeing One - Rock-Surrounded Chest" }, 15 {new Guid("621c284f-cbd0-74c3-f51b-2a9fdde8d4d7"), "Temple of the Seeing One - Rock-Surrounded Chest" },
13 {new Guid("401939a4-41ba-e07e-3ba2-dc22513dcc5c"), "Temple of the Seeing One - Dark Room Chest" }, 16 {new Guid("401939a4-41ba-e07e-3ba2-dc22513dcc5c"), "Temple of the Seeing One - Dark Room Chest" },
14 {new Guid("88d0a7b8-eeab-c45f-324e-f1c7885c41ce"), "Temple of the Seeing One - Shieldy Room Chest" }, 17 {new Guid("88d0a7b8-eeab-c45f-324e-f1c7885c41ce"), "Temple of the Seeing One - Shieldy Room Chest" },
18 {new Guid("c481ee20-662e-6b02-b010-676ab339fc2d"), "Temple of the Seeing One - Health Cicada" },
15 {new Guid("0bce5346-48a2-47f9-89cb-3f59d9d0b7d2"), "Temple of the Seeing One - Boss Chest" }, 19 {new Guid("0bce5346-48a2-47f9-89cb-3f59d9d0b7d2"), "Temple of the Seeing One - Boss Chest" },
16 {new Guid("d41f2750-e3c7-bbb4-d650-fafc190ebd32"), "Temple of the Seeing One - After Statue Left Chest" }, 20 {new Guid("d41f2750-e3c7-bbb4-d650-fafc190ebd32"), "Temple of the Seeing One - After Statue Left Chest" },
17 {new Guid("3167924e-5d52-1cd6-d6f4-b8e0e328215b"), "Temple of the Seeing One - After Statue Right Chest" }, 21 {new Guid("3167924e-5d52-1cd6-d6f4-b8e0e328215b"), "Temple of the Seeing One - After Statue Right Chest" },
diff --git a/AnodyneArchipelago/Plugin.cs b/AnodyneArchipelago/Plugin.cs index f49ba35..d40da7c 100644 --- a/AnodyneArchipelago/Plugin.cs +++ b/AnodyneArchipelago/Plugin.cs
@@ -2,11 +2,16 @@
2using AnodyneSharp.Entities; 2using AnodyneSharp.Entities;
3using AnodyneSharp.Entities.Gadget; 3using AnodyneSharp.Entities.Gadget;
4using AnodyneSharp.Entities.Gadget.Treasures; 4using AnodyneSharp.Entities.Gadget.Treasures;
5using AnodyneSharp.Entities.Interactive;
6using AnodyneSharp.Registry;
7using AnodyneSharp.Utilities;
5using BepInEx; 8using BepInEx;
6using BepInEx.NET.Common; 9using BepInEx.NET.Common;
7using HarmonyLib; 10using HarmonyLib;
8using HarmonyLib.Tools; 11using HarmonyLib.Tools;
9using System; 12using System;
13using System.Collections;
14using System.Collections.Generic;
10using System.Reflection; 15using System.Reflection;
11 16
12namespace AnodyneArchipelago 17namespace AnodyneArchipelago
@@ -85,4 +90,107 @@ namespace AnodyneArchipelago
85 return true; 90 return true;
86 } 91 }
87 } 92 }
93
94 [HarmonyPatch(typeof(Big_Key), nameof(Big_Key.PlayerInteraction))]
95 class BigKeyTouchPatch
96 {
97 // We basically just rewrite this method, because we need to get rid of the part that adds the key to the inventory.
98 static bool Prefix(Big_Key __instance, ref bool __result)
99 {
100 Type keyType = typeof(Big_Key);
101 FieldInfo presetField = keyType.GetField("_preset", BindingFlags.NonPublic | BindingFlags.Instance);
102 EntityPreset preset = presetField.GetValue(__instance) as EntityPreset;
103
104 MethodInfo statesMethod = keyType.GetMethod("States", BindingFlags.NonPublic | BindingFlags.Instance);
105
106 preset.Alive = false;
107 __instance.Solid = false;
108 GlobalState.StartCutscene = (System.Collections.Generic.IEnumerator<AnodyneSharp.States.CutsceneState.CutsceneEvent>)statesMethod.Invoke(__instance, new object[] { });
109 __result = true;
110 return false;
111 }
112 }
113
114 [HarmonyPatch(typeof(Big_Key), "States")]
115 class BigKeyStatesPatch
116 {
117 static void Postfix(Big_Key __instance)
118 {
119 Type keyType = typeof(Big_Key);
120 FieldInfo presetField = keyType.GetField("_preset", BindingFlags.NonPublic | BindingFlags.Instance);
121 EntityPreset preset = presetField.GetValue(__instance) as EntityPreset;
122
123 if (preset.Frame == 0)
124 {
125 ArchipelagoManager.SendLocation("Temple of the Seeing One - Green Key");
126 } else if (preset.Frame == 1)
127 {
128 ArchipelagoManager.SendLocation("Red Grotto - Red Key");
129 } else if (preset.Frame == 2)
130 {
131 ArchipelagoManager.SendLocation("Mountain Cavern - Blue Key");
132 }
133 }
134 }
135
136 [HarmonyPatch(typeof(HealthCicadaSentinel), nameof(HealthCicadaSentinel.Collided))]
137 class HealthCicadaInteractPatch
138 {
139 static void Prefix(TreasureChest __instance)
140 {
141 Type hcsType = typeof(HealthCicadaSentinel);
142 FieldInfo childField = hcsType.GetField("_child", BindingFlags.NonPublic | BindingFlags.Instance);
143 HealthCicada healthCicada = (HealthCicada)childField.GetValue(__instance);
144
145 Type cicadaType = typeof(HealthCicada);
146 FieldInfo presetField = cicadaType.GetField("_preset", BindingFlags.NonPublic | BindingFlags.Instance);
147 EntityPreset preset = presetField.GetValue(healthCicada) as EntityPreset;
148 Plugin.Instance.Log.LogInfo($"Touched cicada: {preset.EntityID.ToString()}");
149 }
150 }
151
152 [HarmonyPatch(typeof(HealthCicada), nameof(HealthCicada.Update))]
153 class HealthCicadaUpdatePatch
154 {
155 static void Postfix(HealthCicada __instance)
156 {
157 Type cicadaType = typeof(HealthCicada);
158 FieldInfo chirpField = cicadaType.GetField("_chirp", BindingFlags.NonPublic | BindingFlags.Instance);
159 FieldInfo sentinelField = cicadaType.GetField("_sentinel", BindingFlags.NonPublic | BindingFlags.Instance);
160
161 HealthCicadaSentinel sentinel = (HealthCicadaSentinel)sentinelField.GetValue(__instance);
162 Type hcsType = typeof(HealthCicadaSentinel);
163 FieldInfo flyDistanceField = hcsType.GetField("_flyDistance", BindingFlags.NonPublic | BindingFlags.Instance);
164 float flyDistance = (float)flyDistanceField.GetValue(sentinel);
165
166 if (__instance.visible && !(bool)chirpField.GetValue(__instance) && flyDistance > 0)
167 {
168 flyDistanceField.SetValue(sentinel, 0f);
169
170 FieldInfo stateField = cicadaType.GetField("_state", BindingFlags.NonPublic | BindingFlags.Instance);
171 stateField.SetValue(__instance, StateLogic(__instance));
172 }
173 }
174
175 static IEnumerator<string> StateLogic(HealthCicada healthCicada)
176 {
177 Type cicadaType = typeof(HealthCicada);
178 FieldInfo presetField = cicadaType.GetField("_preset", BindingFlags.NonPublic | BindingFlags.Instance);
179 EntityPreset preset = presetField.GetValue(healthCicada) as EntityPreset;
180
181 while (!MathUtilities.MoveTo(ref healthCicada.opacity, 0.0f, 0.6f))
182 yield return "FadingOut";
183 preset.Alive = false;
184
185 FieldInfo sentinelField = cicadaType.GetField("_sentinel", BindingFlags.NonPublic | BindingFlags.Instance);
186 HealthCicadaSentinel sentinel = (HealthCicadaSentinel)sentinelField.GetValue(healthCicada);
187
188 sentinel.exists = false;
189
190 if (Locations.LocationsByGuid.ContainsKey(preset.EntityID))
191 {
192 ArchipelagoManager.SendLocation(Locations.LocationsByGuid[preset.EntityID]);
193 }
194 }
195 }
88} 196}