Even More Modifiers  1.0.0.0
A mod for rolling various bonus stats on items
ItemPrefixPatch.cs
Go to the documentation of this file.
1 using System;
2 using Loot.Api.Ext;
3 using Mono.Cecil.Cil;
4 using MonoMod.Cil;
5 using Terraria;
6 
7 namespace Loot.ILEditing
8 {
12  internal class ItemPrefixPatch : ILEdit
13  {
14  public override void Apply(bool dedServ)
15  {
16  IL.Terraria.Item.Prefix += ItemOnPrefix;
17  }
18 
19  private void ItemOnPrefix(ILContext il)
20  {
21  var cursor = new ILCursor(il);
22 
23  // Find !item.accessory check
24  if (!cursor.TryGotoNext(MoveType.Before,
25  i => i.MatchLdarg(0),
26  i => i.MatchLdfld("Terraria.Item", "accessory")))
27  return;
28 
29  // Append our check
30  cursor.Emit(OpCodes.Ldarg_0); // emit item
31  cursor.EmitDelegate<Func<Item, bool>>(IsArmor);
32 
33  // Clone cursor
34  var retCursor = cursor.Clone();
35  // Go after the vanilla false return statement
36  // we may find either a return op or a br (branching) op for debug
37  // in debug there is one ret op at the end of method, with br ops branching to it
38  // so we can match either one and we will be in the right position.
39  retCursor.TryGotoNext(MoveType.After, i => i.OpCode == OpCodes.Ret || i.OpCode == OpCodes.Br);
40 
41  // If our emitted delegate holds true, transfer control to our label
42  cursor.Emit(OpCodes.Brtrue, retCursor.MarkLabel());
43  // We essentially "goto" our new label is the item is armor, skipping the return or branching
44  }
45 
46  private bool IsArmor(Item item) => item.IsArmor();
47  }
48 }