c# - Xamarin.Forms Shell + ReactiveUI 选项卡加载性能(在 Android 上)
问题描述
我已经测试 ReactiveUI 有一段时间了(强烈推荐它!)但最近遇到了一个性能问题,我不确定这是否是由于 ReactiveUI 本身(鉴于它似乎依赖于某些事情的反射)或Xamarin.Forms 应用外壳。切换到内容具有 ReactiveUI 绑定的 Tab 时会有明显的延迟,这在模拟器上运行时会更加明显,但也可以在真实设备上体验(在 Android 6 和 Android 9 设备上测试)。是否有提高 App Shell 选项卡性能的策略?性能问题仅在选项卡的第一次加载时出现。下面的相关代码(基于基本 App Shell Visual Studio 模板的简化示例):
AppShell.Xaml
<?xml version="1.0" encoding="UTF-8"?>
<Shell xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
xmlns:local="clr-namespace:ReactiveXam.Views"
Title="ReactiveXam"
x:Class="ReactiveXam.AppShell"
Visual="Material">
<!-- Your Pages -->
<TabBar>
<Tab Title="Browse" Icon="tab_feed.png">
<ShellContent ContentTemplate="{DataTemplate local:ItemsPage}" />
</Tab>
<Tab Title="About" Icon="tab_about.png">
<ShellContent ContentTemplate="{DataTemplate local:AboutPage}" />
</Tab>
<Tab Title="Test" Icon="tab_about.png">
<ShellContent ContentTemplate="{DataTemplate local:TestPage}" /> <!-- The relevant tab -->
</Tab>
</TabBar>
</Shell>
TestPage.Xaml(TestPageViewModel 是一个继承自 ReactiveObject 的“空”类)
<?xml version="1.0" encoding="utf-8" ?>
<rxui:ReactiveContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
xmlns:rxui="clr-namespace:ReactiveUI.XamForms;assembly=ReactiveUI.XamForms"
xmlns:local="clr-namespace:ReactiveXam.Views"
xmlns:vms="clr-namespace:ReactiveXam.ViewModels"
x:TypeArguments="vms:TestPageViewModel"
x:Class="ReactiveXam.Views.TestPage">
<ContentPage.Content>
<StackLayout>
<Label Text="Welcome to Xamarin.Forms!"
VerticalOptions="CenterAndExpand"
HorizontalOptions="CenterAndExpand" />
<local:Exposure />
</StackLayout>
</ContentPage.Content>
</rxui:ReactiveContentPage>
曝光.Xaml
<?xml version="1.0" encoding="UTF-8"?>
<rxui:ReactiveContentView xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:vms="clr-namespace:ReactiveXam.ViewModels"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
x:TypeArguments="vms:ExposureViewModel"
xmlns:rxui="clr-namespace:ReactiveUI.XamForms;assembly=ReactiveUI.XamForms"
x:Class="ReactiveXam.Views.Exposure">
<StackLayout>
<Label x:Name="balance" />
<Label x:Name="exposure" />
</StackLayout>
</rxui:ReactiveContentView>
曝光.xaml.cs
public partial class Exposure : ReactiveContentView<ExposureViewModel>
{
public Exposure()
{
InitializeComponent();
ViewModel = new ExposureViewModel();
// The code below slows down the loading of the tab (~5x slower).
this.WhenActivated((disposable) =>
{
this.OneWayBind(ViewModel, vm => vm.Exposure, v => v.exposure.Text).DisposeWith(disposable);
this.OneWayBind(ViewModel, vm => vm.Balance, v => v.balance.Text).DisposeWith(disposable);
});
}
}
曝光视图模型
public class ExposureViewModel : ReactiveObject
{
double balance, exposure;
public double Balance
{
get => balance = 500.00d;
set => this.RaiseAndSetIfChanged(ref balance, value);
}
public double Exposure
{
get => exposure = 25.00d;
set => this.RaiseAndSetIfChanged(ref exposure, value);
}
public ExposureViewModel()
{
}
}
解决方案
好吧,我已经把很多时间花在了很棒的 Xamarin Forms Shell 上,我认为这本身就是你现在谈论的性能延迟的原因。
当您阅读 Microsoft 文档时,它清楚地表明:
在 Shell 应用程序中,作为 ShellContent 对象的子级的每个 ContentPage 都是在应用程序启动期间创建的。使用这种方法添加额外的 ShellContent 对象将导致在应用程序启动期间创建额外的页面,这可能会导致糟糕的启动体验。但是,Shell 还能够根据导航创建按需页面。有关详细信息,请参阅高效页面加载。
好消息是您可以通过按需加载这些页面来解决此问题,如下所示:https ://docs.microsoft.com/en-us/xamarin/xamarin-forms/app-fundamentals/shell/tabs#efficient -页面加载
基本上,这可以通过使用 DataTemplate 标记扩展将每个 ContentPage 转换为 DataTemplate 然后将结果设置为 ShellContent.ContentTemplate 属性值来完成。
推荐阅读
- c# - 将数据网格列绑定到视图模型
- offline - 无法在离线模式下使用 gridsome 网站
- linux - 不能通过 SPIDEV 发送超过一个字节
- java - 缺少哪个代码,可点击的菜单项不起作用
- javascript - Javascript,在 React 应用程序中分配给函数组件中的 {},代码审查
- java - Spring Boot WAR 部署
- jquery - 没有 .fadeIn() 和 .fadeOut() 的淡化 div
- offline - 无法在离线模式下使用 gatsby 网站
- ruby - 有没有办法重新定义块内的方法?
- python-2.7 - 如何在使用 for 语句创建联合路径之前检查是否存在联合路径