Я работаю над проектом (использующим Xna), который, в основном, читает файл содержимого XML для создания обработчиков событий, которые обрабатывают различные типы входных событий.Файл XML выглядит примерно так:
<InputMapping>
<InputType>Microsoft.Xna.Framework.Input.Keys, Microsoft.Xna.Framework, Version=3.1.0.0, Culture=neutral, PublicKeyToken=6d5c3888ef60e27d</InputType>
<Combination>Up W</Combination>
<CombinationType>Any</CombinationType>
<Handlers>
<Handler>MoveUp</Handler>
<Handler>ScrollMenuUp</Handler>
</Handlers>
</InputMapping>
«MoveUp» и «ScrollMenuUp» - это имена двух методов, которые я хочу иметь возможность обрабатывать событие, возникающее при «вверх» и / или «Нажаты клавиши W, и я пометил их содержащий класс с помощью специального атрибута, говорящего так.Сгенерированная «карта ввода» добавляется в список карт ввода, которые обновляются каждый кадр в игре.Когда комбинация ввода (которая может быть щелчком мыши, движением колеса прокрутки, движением мыши и т. Д., В зависимости от типа отображения ввода) выполняется, событие вызывается и обрабатывается методами, перечисленными в XMLfile.
Чтобы найти методы, на которые ссылается XML-файл, я изначально планировал перебирать экспортируемые типы в выполняющейся сборке с использованием отражения, находить статические классы, к которым был применен мой пользовательский атрибути сохраните все свои открытые статические методы, которые соответствуют сигнатуре делегата рассматриваемого события, в Словаре, используя их имена для использования при последующей загрузке входной карты, ссылающейся на те же методы.Для сборки выпуска я напишу этот список методов в файл, чтобы существенно сократить время загрузки, но для отладки я хочу, чтобы этот список доступных обработчиков событий оставался в курсе моих ревизий.
Это работает отлично, и на удивление занимает меньше времени, чем я ожидал.Однако я не могу понять, как расширить этот подход для включения общих делегатов: у меня есть универсальный делегат с именем InputHandler<T>
, который выглядит следующим образом:
public delegate void InputHandler<T>(T input, GameTime gameTime) where T : struct;
Я могу получить подпись делегата простохорошо, но моя проблема в том, что я не знаю, как получить классы, которые построены из универсальных типов, которые содержат методы, которые могут быть представлены InputHandler<T>
.Проще говоря, у меня есть класс с именем InputHandlers<T>
, который выглядит следующим образом:
[MyInputHandlerAttribute]//This tells my XML-loading method to look in this class for event handler candidates
public static class InputHandlers<T>
where T : struct
{
public static void HandleInput<T>(T input, GameTime gameTime)
{
/*
* An input event would be handled here.
* The type of input event handled would depend entirely on the assembly-qualified
* name provided in the "<InputType>" element of the XML file.
* This kind of non-specific input handling might not make sense, but it has its worthwhile uses:
* serializing input for network transmission
* (using some interface that T would be constrained to implement) is the use I have in mind.
*/
}
}
, и я хочу иметь возможность просто набрать <Handler>HandleInput</Handler>
в моем XML-файле и найти MethodInfo, который соответствуетметод, определенный в классе, построенном из InputHandlers<T>
с общим аргументом, соответствующим событию, которое я хочу обработать (того же типа, что и T, используемый в объявлении InputHandler<T>
события, которое я могу извлечь только из сборкиимя, указанное в файле XML).
Я знаю (из спецификаций C #), что открытых типов не существует во время выполнения, так как я могу получить список закрытых типов, созданных из моего универсального класса