重置使用 MEF 加载的控件

发布于 2024-10-01 10:32:27 字数 1493 浏览 0 评论 0原文

我已经使用 MEF 加载外部 XAP,效果很好。 但是,当我导航离开包含已加载控件的页面,然后返回到该页面时,该控件处于我离开时的确切状态。

有时这很棒,但不适合我正在从事的项目。

如何将控件重置为初始状态?

控件已(成功)加载到此处:

 <ItemsControl x:Name="content"/>

这是在 XAML 标记中

我有一个 On NavigatedFrom 方法:

protected override void OnNavigatedFrom(NavigationEventArgs e)
{
    content.Items.Clear();
}

这成功删除了控件,与添加此控件之前一样,当我返回页面时,它崩溃了,告诉我该控件已经是一个元素的子元素。

这是完整的页面代码:

public partial class Wizard : IPartImportsSatisfiedNotification
{
    public Wizard()
    {
        InitializeComponent();
        CompositionInitializer.SatisfyImports(this);

        var controlToLoad = IsolatedStorageHelper.GetValue("control");

        if (!String.IsNullOrEmpty(controlToLoad))
        {
            CatalogService.AddXap(controlToLoad + ".xap");
        }
    else
    {
        NavigationService.Navigate(new Uri("/ServiceSelector", UriKind.Relative));
    }
}

protected override void OnNavigatedFrom(NavigationEventArgs e)
{
    content.Items.Clear();
}

[Import]
public IDeploymentCatalogService CatalogService { get; set; }

[ImportMany(AllowRecomposition = true)]
public Lazy<UserControl>[] MefModuleList { get; set; }

#region IPartImportsSatisfiedNotification Members

public void OnImportsSatisfied()
{
    MefModuleList.ToList()
        .ForEach(module =>
            content.Items.Add(module.Value)
        );
}

#endregion
}

有人有什么想法吗?

谢谢,

I have used MEF to load in external XAPs, this works great.
But when I navigate away from the page with the loaded control, then go back to it, the control is in the exact state I left it.

Now sometimes this is great, but not for the project I working on.

How do I reset the control to its initial state?

The control is loaded (successfuly) into here:

 <ItemsControl x:Name="content"/>

This is in the XAML markup

I have an On NavigatedFrom Method:

protected override void OnNavigatedFrom(NavigationEventArgs e)
{
    content.Items.Clear();
}

This successfuly removed the control, as before adding this, when I went back to the page it crashed telling me the control was already a child of an element.

here is the full pages code:

public partial class Wizard : IPartImportsSatisfiedNotification
{
    public Wizard()
    {
        InitializeComponent();
        CompositionInitializer.SatisfyImports(this);

        var controlToLoad = IsolatedStorageHelper.GetValue("control");

        if (!String.IsNullOrEmpty(controlToLoad))
        {
            CatalogService.AddXap(controlToLoad + ".xap");
        }
    else
    {
        NavigationService.Navigate(new Uri("/ServiceSelector", UriKind.Relative));
    }
}

protected override void OnNavigatedFrom(NavigationEventArgs e)
{
    content.Items.Clear();
}

[Import]
public IDeploymentCatalogService CatalogService { get; set; }

[ImportMany(AllowRecomposition = true)]
public Lazy<UserControl>[] MefModuleList { get; set; }

#region IPartImportsSatisfiedNotification Members

public void OnImportsSatisfied()
{
    MefModuleList.ToList()
        .ForEach(module =>
            content.Items.Add(module.Value)
        );
}

#endregion
}

Anyone any ideas?

Thanks,

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

飘落散花 2024-10-08 10:32:27

一个简单的解决方法是使用 ExportFactory 而不是 Lazy 来避免整个问题:创建一个新实例而不是重用旧实例。只需确保丢弃的实例被 GC 处理而不是堆积起来(编辑:新实例在 ExportLifetimeContext 实例中交给您,它管理对象的生命周期)。

现在的问题听起来好像那个老孩子仍然认为他有父母。在你再次将他添加回容器之前(最好是在你将他移走时),你需要告诉他他现在失去了父母。不过,UserControl.Parent 是只读的。也许在父级上调用RemoveLogicalChild?我还没有测试过这一点,但如果 ExportFactory 的行为不能让你满意的话,一般的途径似乎值得探索。

A simple fix would be to avoid the whole issue by using ExportFactory rather than Lazy: Create a new instance instead of reusing the old one. Just make sure the discarded instances get GC'd instead of piling up (EDIT: The new instances are handed to you in ExportLifetimeContext instances, which mange the lifespan of the object).

What's going wrong now sounds like the old child still thinks he has a parent. Before you add him back to the container again (preferably right at the point when you remove him), you need to tell him he's now parentless. UserControl.Parent is read-only, though. Maybe call RemoveLogicalChild on the parent? I haven't tested that, but the general avenue seems worth exploring, if the ExportFactory caper doesn't float your boat.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文