在我的 UWP 应用中,我不断从第 1 页导航到第 2 页,再从第 2 页导航到第 1 页,并且此导航循环再次在两个页面中的提交按钮上重复。在启动应用程序中,它的性能很好,但是当页面进一步导航时,它会占用更多内存,并且在导航 15 或 20 次后应用程序会变慢。我尝试通过减小导航缓存的大小来删除导航缓存,但它没有帮助,在我的研究中,我发现如果导航模式设置为启用,它会减少一些内存使用量。但是当我保持启用它时,以前的数据不会消失。我需要一个解决方案来删除以前页面的内存,并使我的应用程序即使在导航多次后也能使用更少的内存。
问题是 UWP 引擎不会破坏您的页面,即使它不再位于导航堆栈中。
但是有解决方案:
- 不要在 XAML 代码中使用
NavigationCacheMode
- 在每个页面上必须覆盖
OnNavigatedTo()
,当NavigationMode
为"新建"时,更改NavigationCacheMode
"必需
" - 在每个页面上必须覆盖
OnNavigatingFrom()
,当NavigationMode
为"返回"时,更改"NavigationCacheMode
禁用">
使用此机制,可以实现以下目标:导航堆栈上的每个页面都是缓存=必需的,导航堆栈上没有的每个页面都是缓存=禁用。
但是当用户按转发时,页面是新分配的,因此以前的状态会丢失。
在某些情况下,禁用缓存模式不足,UWP 仍将页面保留在内存中。在这种情况下,我们必须删除缓存。如果我们将当前帧缓存大小重置为零并恢复为原始,我们可以做到这一点。
这是我在每个页面中的代码:
protected override void OnNavigatedTo( NavigationEventArgs navigationEvent )
{
// call the original OnNavigatedTo
base.OnNavigatedTo( navigationEvent );
// when the dialog displays then we create viewmodel and set the cache mode
if( CreatedViewModel == null || navigationEvent.NavigationMode == NavigationMode.New )
{
// set the cache mode
NavigationCacheMode = NavigationCacheMode.Required;
// create viewmodel
CreatedViewModel = CreateViewModel( navigationEvent.Parameter );
DataContext = CreatedViewModel;
CreatedViewModel.InitializeAsync().ConfigureAwait( false );
}
}
protected override void OnNavigatingFrom( NavigatingCancelEventArgs navigationEvent )
{
// call the original OnNavigatingFrom
base.OnNavigatingFrom( navigationEvent );
// when the dialog is removed from navigation stack
if( navigationEvent.NavigationMode == NavigationMode.Back )
{
// set the cache mode
NavigationCacheMode = NavigationCacheMode.Disabled;
ResetPageCache();
}
}
private void ResetPageCache()
{
int cacheSize = ((Frame)Parent).CacheSize;
((Frame)Parent).CacheSize = 0;
((Frame)Parent).CacheSize = cacheSize;
}
一些注意事项:当您创建一个 BasePage 并将此代码放入其中时会更舒适,您可以在每个页面中从此 BasePage 派生。