【问题标题】:Caliburn.Mirco Simple Container Multiple Interface InstancesCaliburn.Mirco 简单容器多接口实例
【发布时间】:2022-01-04 19:45:46
【问题描述】:

我实际上是在尝试使用 Caliburn Micro 的简单容器运行选项卡控件,其中每个选项卡视图模型都在 c# 中实现了一个接口“IMainScreenTabItem”。

在设置容器时,我可以这样做:

container.AllTypesOf<IMainScreenTabItem>(Assembly.GetExecutingAssembly());

这将允许我在选项卡控件视图模型的构造函数中获取所有实现 IMainScreenTabItem 的视图模型,如下所示:

public TabControlViewModel(IEnumerable<IMainScreenTabItem> tabs){ Items.AddRange(tabs); }

这个特定应用程序的问题是,当 TabControlViewModel 被释放并且 .AllTypesOf 方法将它们注册为单例时,我不希望实现保持为单例。

我可以像这样对每个视图模型进行硬编码来创建它们:

container.Instance(container)
            .PerRequest<IMainScreenTabItem, TabItem1>()
            .PerRequest<IMainScreenTabItem, TabItem2>();

等等..但感觉有点乱。

我在想这样的事情:

var tabs = GetType().Assembly.GetTypes()
            .Where(type => type.IsClass)
            .Where(type => !type.IsAbstract)
            .Where(type => type.GetInterface(nameof(IMainScreenTabItem)) != null);

tabs.ToList().ForEach(tab => container.RegisterPerRequest(typeof(IMainScreenTabItem), tab.ToString(), tab));

问题在于 .RegisterPerRequest 不允许我像 .PerRequest 那样拥有单个接口的多个实现。

Caliburn Micro 的网站将差异描述为“每个请求注册会导致每个请求创建一次返回的实体。这意味着对同一实体的两个不同请求将导致创建两个不同的实例。” https://caliburnmicro.com/documentation/simple-container

所以我想做这样的事情:

tabs.ToList().ForEach(tab => container.PerRequest<IMainScreenTabItem, tab>());

但显然我得到 'tab 是一个变量,但被用作类型' 错误消息。

对此的任何想法将不胜感激!这是我的第一个 Caliburn Micro 项目,所以我可能只是缺少一些简单的东西。

提前致谢!

【问题讨论】:

    标签: c# wpf tabcontrol caliburn.micro


    【解决方案1】:

    你不能使用工厂方法来解析程序集中的IMainScreenTabItem 的所有实现吗?:

    container.Handler<TabControlViewModel>(container =>
    {
        var tabs = AppDomain.CurrentDomain.GetAssemblies()
            .SelectMany(s => s.GetTypes())
            .Where(t => t.GetInterfaces().Contains(typeof(IMainScreenTabItem)))
            .Select(t => (IMainScreenTabItem)Activator.CreateInstance(t))
            .ToArray();
        return new TabControlViewModel();
    });
    

    【讨论】:

    • 我从来没有用过那种方法!很酷的代码。创建选项卡时是否适合使用 IoC.Get(),或者我应该如何获取选项卡视图模型?
    • 从程序集中获取实现接口的类型,然后使用Activator.CreateInstance 创建它们的实例。我用一个例子编辑了我的答案。
    猜你喜欢
    • 2016-03-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-03-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-03-07
    相关资源
    最近更新 更多