.NET 8 MAUI使用GoToAsync导航时ViewModel未重置的问题
解决.NET 8 MAUI Shell导航中页面ViewModel旧数据残留问题
问题根源是MAUI Shell默认会缓存页面实例,调用GoToAsync("..")只是将页面从导航栈顶移除,并未销毁实例,再次导航时会复用原有页面和ViewModel,导致旧数据残留。以下是几种可行的解决方式:
方法1:在页面导航时重置ViewModel数据
利用页面的OnNavigatedTo生命周期方法,每次进入页面时根据导航参数重新加载数据或重置表单:
页面代码(WordEdit.xaml.cs)
protected override void OnNavigatedTo(NavigatedToEventArgs args) { base.OnNavigatedTo(args); // 解析导航参数中的WordID if (Shell.Current.CurrentState.Location.Queries.TryGetValue("WordID", out var wordIdStr) && int.TryParse(wordIdStr, out var wordId)) { var vm = BindingContext as WordEditViewModel; vm?.ReloadWordData(wordId); // 重新加载目标数据 // 若为新增场景,可调用重置方法:vm?.ResetForm(); } }
ViewModel代码示例
public class WordEditViewModel : ObservableObject { private readonly IWordService _wordService; public int WordID { get; set; } public string WordContent { get; set; } = string.Empty; public WordEditViewModel(IWordService wordService) { _wordService = wordService; } public void ReloadWordData(int wordId) { // 从数据源获取最新数据并更新ViewModel属性 var targetWord = _wordService.GetWordById(wordId); WordID = targetWord.Id; WordContent = targetWord.Content; // 其他字段同步更新... } public void ResetForm() { // 清空所有表单字段(新增场景用) WordID = 0; WordContent = string.Empty; } }
方法2:禁用页面导航缓存
直接设置WordEdit页面的缓存模式为禁用,让每次导航都创建新的页面和ViewModel实例:
方式A:在页面XAML中设置
<ContentPage x:Class="YourApp.Pages.WordEdit" NavigationCacheMode="Disabled"> <!-- 页面内容 --> </ContentPage>
方式B:在路由注册时设置(AppShell.xaml.cs)
public AppShell() { InitializeComponent(); Routing.RegisterRoute(nameof(WordEdit), typeof(WordEdit), new Dictionary<string, object> { { nameof(NavigationCacheMode), NavigationCacheMode.Disabled } }); }
方法3:返回时移除页面栈中的实例
在WordEdit页面保存完成后,先将当前页面从导航栈中移除,再返回上一页:
// 保存逻辑完成后执行 var navigationStack = Shell.Current.Navigation.NavigationStack; if (navigationStack.Contains(this)) { Shell.Current.Navigation.RemovePage(this); } await Shell.Current.GoToAsync("..", true);
内容的提问来源于stack exchange,提问作者Enrico
相关产品推荐
相关产品推荐

