Created
January 2, 2020 15:07
-
-
Save pardeike/9f68fd3f05a04c2081c1b506a0ff9796 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections; | |
public class Program | |
{ | |
// simulating a Harmony Passthrough Postfix | |
// (run it here: https://dotnetfiddle.net/qMPu6m) | |
// | |
// A passthrough postfix can be used to execute code between yields | |
// of an enumerator method. Normally, you cannot patch those methods | |
// because the compiler turns them into hidden state machine classes | |
// and patching the original method will just influence the small stub | |
// method that creates an instance of that compiler generated class | |
// | |
// This example will visualize how you can use the fact that enumerators | |
// are in fact "generator functions" that get their results "pulled" out | |
// of them one-by-one instead of running like normal methods. | |
// | |
// Harmony uses this to wrap the original with the enumerator that is | |
// generated when you create a PASSTHROUGH POSTFIX: | |
// -------------------------------------------------------- | |
// static T Postfix(T varname, ...normal postfix arguments) | |
// -------------------------------------------------------- | |
// This works for any T but is especially useful for T = IEnumerator | |
public static void Main() | |
{ | |
Console.WriteLine("\n# Original"); | |
var it1 = Original(); | |
while(it1.MoveNext()) | |
Console.WriteLine(it1.Current); | |
Console.WriteLine("\n# With Passthrough Postfix)"); | |
var it2 = Postfix(Original()); | |
while(it2.MoveNext()) | |
Console.WriteLine(it2.Current); | |
} | |
static IEnumerator Original() | |
{ | |
Console.WriteLine("Apple"); | |
yield return 10; | |
Console.WriteLine("Banana"); | |
yield return 20; | |
Console.WriteLine("Cherry"); | |
yield return 30; | |
Console.WriteLine("Melon"); | |
yield return 40; | |
} | |
static IEnumerator Postfix(IEnumerator e) | |
{ | |
var n = 0; | |
while(e.MoveNext()) | |
{ | |
var element = e.Current; | |
if (n == 2) | |
Console.WriteLine("[PRE]"); | |
yield return element; | |
if (n == 2) | |
Console.WriteLine("[POST]"); | |
n += 1; | |
} | |
} | |
} | |
// # Original | |
// Apple | |
// 10 | |
// Banana | |
// 20 | |
// Cherry | |
// 30 | |
// Melon | |
// 40 | |
// | |
// # With Passthrough Postfix) | |
// Apple | |
// 10 | |
// Banana | |
// 20 | |
// Cherry | |
// [PRE] | |
// 30 | |
// [POST] | |
// Melon | |
// 40 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment