旧的ViewModel重用而不是构建一个新的ViewModel

时间:2014-04-08 10:34:38

标签: android mvvmcross activity-lifecycle

有时当活动被销毁时(不确定为什么,我假设的内存压力),会创建一个新活动,但重新使用绑定到死活动的旧视图模型。

的活动:

[Activity( 
    LaunchMode = LaunchMode.SingleTask,
    ConfigurationChanges = ConfigChanges.Orientation | ConfigChanges.ScreenSize)]
public class HomeView : MvxTabsFragmentActivity
{
    protected override void OnCreate(Bundle bundle)
    {
        Log.Info("On HomeView created");
        base.OnCreate(bundle);
    }

    protected override void OnDestroy()
    {
        base.OnDestroy();
        Log.Info("On HomeView destroyed");
        this.HomeViewModel.CleanUp();
    }        
}

视图模型:

public class HomeViewModel : MvxViewModel
{
    public HomeViewModel(
        IMvxMessenger messenger,
        IUserInteraction userInteraction,
        DashboardViewModel dashboardViewModel,
        AlertSettingsViewModel alertSettingsViewModel)
    {
        Log.Info("Building home view model");
    }

    public void CleanUp()
    {
        Log.Info("HomeViewModel => Clean-up");
    }       
}

App.cs:

    public override void Initialize()
    {
        this.CreatableTypes().EndingWith("ViewModel").AsTypes().RegisterAsDynamic();

        this.RegisterAppStart<HomeViewModel>();

        TaskScheduler.UnobservedTaskException +=
            (sender, eventArgs) =>
            Log.Error("An Unobserved exception has been raised by a task", eventArgs.Exception);
    }

调试输出:

On HomeView created
Building home view model
...
On HomeView destroyed
HomeViewModel => Clean-up
...
On HomeView created
[here: no "Building view model" message]

也许是SingleTask活动?

有没有办法(使用IoC或其他方法)在每个HomeView创建时获得一个全新的视图模型?

修改

我在MvxActivityViewExtensions.cs

上运行了这个方法
public static void OnViewCreate(this IMvxAndroidView androidView, Bundle bundle)
{
  MvxActivityViewExtensions.EnsureSetupInitialized(androidView);
  MvxActivityViewExtensions.OnLifetimeEvent(androidView, (Action<IMvxAndroidActivityLifetimeListener, Activity>) ((listener, activity) => listener.OnCreate(activity)));
  IMvxViewModel cached = Mvx.Resolve<IMvxSingleViewModelCache>().GetAndClear(bundle);
  IMvxView view = (IMvxView) androidView;
  IMvxBundle savedState = MvxActivityViewExtensions.GetSavedStateFromBundle(bundle);
  MvxViewExtensionMethods.OnViewCreate(view, (Func<IMvxViewModel>) (() => cached ?? MvxActivityViewExtensions.LoadViewModel(androidView, savedState)));
}

那么这是否意味着我的视图模型被缓存了?如何禁用此缓存?

1 个答案:

答案 0 :(得分:1)

这在[{3}}

中的Wiki中有所介绍

默认情况下,每次请求一个时,MvvmCross都会构建一个新的ViewModel,并使用CIRS序列 - Construction-Init-ReloadState-Start - 初始化该ViewModel。

如果要为一个或多个ViewModel类型覆盖此行为,则可以通过提供自己的IMvxViewModelLocator实现在App对象中执行此操作。

例如,您可以实现

public class MyViewModelLocator
  : MvxDefaultViewModelLocator
{
    private SpecialViewModel _special = new SpecialViewModel();

    public override bool TryLoad(Type viewModelType, IDictionary<string, string> parameterValueLookup,
                                 out IMvxViewModel model)
    {
        if (viewModelType == typeof(SpecialViewModel))
        {
            model = _special;
            return true;
        }
        else if (viewModelType == typeof(FooViewModel))
        {
            model = new FooViewModel(_special);
            return true;
        }

        return base.TryLoad(viewModelType, parameterValueLookup, out model);
    }
}

然后可以在App.cs中返回:

protected override IMvxViewModelLocator CreateDefaultViewModelLocator()
{
    return new MyViewModelLocator();
}