You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

68 lines
2.2 KiB

using ReactiveUI;
using System;
using System.Diagnostics;
using System.Linq;
namespace MyAvaloniaApp.Views;
/// <summary>
/// 视图定位器,用于将 ViewModel 映射到对应的 View
/// </summary>
public class ViewLocator : IViewLocator
{
/// <summary>
/// 根据 ViewModel 类型解析对应的 View
/// </summary>
public IViewFor? ResolveView<T>(T? viewModel, string? contract = null)
{
if (viewModel == null)
{
Debug.WriteLine("[ViewLocator] ViewModel is null");
return null;
}
var viewModelType = viewModel.GetType();
Debug.WriteLine($"[ViewLocator] Resolving View for ViewModel: {viewModelType.FullName}");
// 将 ViewModel 名称转换为 View 名称
var viewModelName = viewModelType.Name; // 只获取类名
// 处理多种命名模式
var viewName = viewModelName
.Replace("PageViewModel", "PageView")
.Replace("ViewModel", "View");
Debug.WriteLine($"[ViewLocator] Looking for View: {viewName}");
Debug.WriteLine($"[ViewLocator] ViewModel Namespace: {viewModelType.Namespace}");
// 获取与 ViewModel 在同一命名空间下的 View
var assembly = viewModelType.Assembly;
var targetNamespace = viewModelType.Namespace?.Replace(".ViewModels", ".Views");
Debug.WriteLine($"[ViewLocator] Target namespace: {targetNamespace}");
var viewType = assembly.GetTypes()
.FirstOrDefault(t => t.Name == viewName && t.Namespace == targetNamespace);
if (viewType == null)
{
Debug.WriteLine($"[ViewLocator] View not found: {viewName} in {targetNamespace}");
return null;
}
Debug.WriteLine($"[ViewLocator] Found View: {viewType.FullName}");
var view = Activator.CreateInstance(viewType) as IViewFor;
if (view == null)
{
Debug.WriteLine("[ViewLocator] Failed to create View instance");
}
else
{
Debug.WriteLine($"[ViewLocator] Successfully created View: {view.GetType().FullName}");
}
return view;
}
}