WinUI 3.0 + .NET 9 Native AOT下ListView/ItemsRepeater抛出ArgumentException问题
WinUI 3.0 + .NET 9 Native AOT下ListView/ItemsRepeater抛出ArgumentException的解决方法
在WinUI 3.0结合.NET 9启用Native AOT发布时,使用ListView或ItemsRepeater会抛出ArgumentException,非AOT模式下代码运行完全正常。更换为ObservableList或字符串数组作为数据源后问题仍存在,使用ItemsRepeater时还会提示“Argument 'source' is not a supported vector”。
解决方案
1. 使用WinRT兼容的集合类型
Native AOT环境下,WinUI控件无法自动识别普通.NET集合的元数据,改用WinRT原生集合类型可直接解决问题:
// 替换原List<string>为ObservableVector<string> Repeater.ItemsSource = new Microsoft.UI.Xaml.Data.ObservableVector<string> { "Item 1", "Item 2", "Item 3", "Item 4", "Item 5" };
2. 保留.NET集合的AOT元数据
若想继续使用.NET集合类型,需通过rd.xml文件显式保留元数据:
- 在项目根目录创建
rd.xml文件,添加以下内容:
<Directives xmlns="http://schemas.microsoft.com/netfx/2013/01/metadata"> <Application> <Assembly Name="System.Collections" Dynamic="Required All" /> <Type Name="System.Collections.Generic.List`1" Dynamic="Required All" /> <Type Name="System.String[]" Dynamic="Required All" /> </Application> </Directives>
- 在项目配置中引用该文件:
<PropertyGroup> <RdXmlFile>rd.xml</RdXmlFile> </PropertyGroup>
3. 检查运行时封送与版本更新
- 确保
DisableRuntimeMarshalling设为false(你的配置已满足),避免集合类型封送失败。 - 升级.NET 9和WinUI 3到最新预览版,部分Native AOT集合兼容性问题可能已被修复。
问题复现代码
XAML代码
<?xml version="1.0" encoding="utf-8"?> <UserControl x:Class="TestProject.UserControls.Home.AOTSourceTest" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:TestProject.UserControls.Home" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <UserControl.Resources> <DataTemplate x:Key="ItemTemplate" x:DataType="x:String"> <TextBlock Text="{x:Bind}" /> </DataTemplate> </UserControl.Resources> <Grid> <ListView Grid.Row="1" x:Name="Repeater" ItemTemplate="{StaticResource ItemTemplate}" /> </Grid> </UserControl>
C#代码
using Microsoft.UI.Xaml.Controls; using System.Collections.Generic; namespace TestProject.UserControls.Home { public sealed partial class AOTSourceTest : UserControl { public AOTSourceTest() { InitializeComponent(); Repeater.Loaded += AOTSourceTest_Loaded; } private void AOTSourceTest_Loaded(object sender, Microsoft.UI.Xaml.RoutedEventArgs e) { Repeater.ItemsSource = new List<string> { "Item 1", "Item 2", "Item 3", "Item 4", "Item 5" }; } } }
项目配置
<PropertyGroup> <OutputType>WinExe</OutputType> <TargetFramework>net9.0-windows10.0.26100.0</TargetFramework> <TargetPlatformMinVersion>10.0.17763.0</TargetPlatformMinVersion> <RootNamespace>TestProject</RootNamespace> <ApplicationManifest>app.manifest</ApplicationManifest> <UseWinUI>true</UseWinUI> <EnableMsixTooling>true</EnableMsixTooling> <PublishAot>true</PublishAot> <DisableRuntimeMarshalling>false</DisableRuntimeMarshalling> <PublishTrimmed>false</PublishTrimmed> <EnablePreviewFeatures>true</EnablePreviewFeatures> </PropertyGroup>
错误堆栈
System.ArgumentException: Value does not fall within the expected range. at WinRT.ExceptionHelpers.<ThrowExceptionForHR>g__Throw|38_0(Int32 hr) at WinRT.ExceptionHelpers.ThrowExceptionForHR(Int32 hr) at ABI.Microsoft.UI.Xaml.Controls.IItemsControlMethods.set_ItemsSource(IObjectReference _obj, Object value) at Microsoft.UI.Xaml.Controls.ItemsControl.set_ItemsSource(Object value) at TestProject.UserControls.Home.AOTSourceTest.AOTSourceTest_Loaded(Object sender, RoutedEventArgs e) at WinRT._EventSource_global__Microsoft_UI_Xaml_RoutedEventHandler.EventState.<GetEventInvoke>b__1_0(Object sender, RoutedEventArgs e) at ABI.Microsoft.UI.Xaml.RoutedEventHandler.Do_Abi_Invoke(IntPtr thisPtr, IntPtr sender, IntPtr e)
内容的提问来源于stack exchange,提问作者Felix
相关产品推荐
相关产品推荐

