MVP パターンを使用してアプリケーションを開発しようとしています。
問題は、すべてのコードを手動で配線することです。必要なコードを減らしたいと思っていました。別のソリューションをコピーしようとしましたが、作業できませんでした。私はWinformsを使用しており、ソースとして使用していたソリューションはWPFを使用しています。
それはいくつかの規則で物事を配線します:
ビュー イベントは名前で結び付けられます。例: ビューの「Loaded」イベントは、プレゼンターの「OnLoaded()」メソッドに接続されます。ボタン コマンドは名前で接続されます。例: MoveNext" ボタンは "OnMoveNext()" メソッドに接続されます。グリッドのダブルクリックは名前で接続されます。例: "Actions" のダブルクリックは "OnActionsChoosen(ToDoAction)" に接続されます。
WPF の作業コードは次のとおりです。
private static void WireListBoxesDoubleClick(IPresenter presenter)
{
var presenterType = presenter.GetType();
var methodsAndListBoxes = from method in GetActionMethods(presenterType)
where method.Name.EndsWith("Choosen")
where method.GetParameters().Length == 1
let elementName = method.Name.Substring(2, method.Name.Length - 2 /*On*/- 7 /*Choosen*/)
let matchingListBox = LogicalTreeHelper.FindLogicalNode(presenter.View, elementName) as ListBox
where matchingListBox != null
select new {method, matchingListBox};
foreach (var methodAndEvent in methodsAndListBoxes)
{
var parameterType = methodAndEvent.method.GetParameters()[0].ParameterType;
var action = Delegate.CreateDelegate(typeof(Action<>).MakeGenericType(parameterType),
presenter, methodAndEvent.method);
methodAndEvent.matchingListBox.MouseDoubleClick += (sender, args) =>
{
var item1 = ((ListBox)sender).SelectedItem;
if(item1 == null)
return;
action.DynamicInvoke(item1);
};
}
}
private static void WireEvents(IPresenter presenter)
{
var viewType = presenter.View.GetType();
var presenterType = presenter.GetType();
var methodsAndEvents =
from method in GetParameterlessActionMethods(presenterType)
let matchingEvent = viewType.GetEvent(method.Name.Substring(2))
where matchingEvent != null
where matchingEvent.EventHandlerType == typeof(RoutedEventHandler)
select new { method, matchingEvent };
foreach (var methodAndEvent in methodsAndEvents)
{
var action = (Action)Delegate.CreateDelegate(typeof(Action),
presenter, methodAndEvent.method);
var handler = (RoutedEventHandler)((sender, args) => action());
methodAndEvent.matchingEvent.AddEventHandler(presenter.View, handler);
}
}
private static IEnumerable<MethodInfo> GetActionMethods(Type type)
{
return from method in type.GetMethods(BindingFlags.DeclaredOnly | BindingFlags.Public | BindingFlags.Instance)
where method.Name.StartsWith("On")
select method;
}
private static IEnumerable<MethodInfo> GetParameterlessActionMethods(Type type)
{
return from method in GetActionMethods(type)
where method.GetParameters().Length == 0
select method;
}
とにかく、それを WinForm アプリに移植しようとしましたが、成功しませんでした。を に変更しましたRoutedEventHandlers
がEventHandlers
、 をどうすればよいかわかりませんでしたLogicalTreeHelper
。
私はこれにちょっと立ち往生しています。手動で行うこともできましたが、このミニフレームワークは非常に巧妙で、ほとんどクレイジーであることがわかりました。
PS: ソースはhttp://msdn.microsoft.com/en-us/magazine/ee819139.aspxです
編集
私は何かに気づきました。私は頭がおかしいわけではありません。上記のコードはあまりテストに適していませんね。