如何使用WinRT打开打包文件
我试图弄清楚如何将一些解析xml文件的.Net代码移植到WinRT。 到目前为止,借助给定的System.Uri无法转换为Windows.Foundation.Uri ,我有以下代码。 不过,在我创建Uri之后,我立即陷入困境:
static readonly Uri ResourcesBase = new Uri(@"ms-resource://MyAssembly/"); public override async void Load() { Uri uri = new Uri(ResourcesBase, filePath); // filePath = "Data//world.xml"; XmlLoadSettings settings = new XmlLoadSettings() { ValidateOnParse = false }; XmlDocument xmlDoc = await XmlDocument.LoadFromUriAsync(uri, settings); foreach (IXmlNode xmlNode in xmlDoc.ChildNodes) { ProcessNode(xmlNode); } }
当我尝试调用XmlDocument.LoadFromUriAsyn(uri)时,我得到一个未处理的exception:
ArgumentException未被用户代码处理 – 值不在预期范围内。
有人觉得WinRT的一切都要难10倍吗?
编辑:
我已经尝试了以下所有字符串,并得到完全相同的错误:
Uri uri = new Uri("ms-resource://MyAssembly//" + filePath); Uri uri = new Uri("ms-resource://MyAssembly/" + filePath); Uri uri = new Uri("d:\\projects\\crystal\\" + filePath); // A valid absolute path
项目设置:
项目
- 属性
- 参考
- 资产
- 数据
- world.xml
- 源代码…
在代码中:
filePath = "Data\\world.xml";
我也尝试将xml文件放在assset \ data下,只放置资产。 似乎没什么区别。
另外,我将xml的Build Action设置为“Content”。 那是对的吗? 我能想到的另一件事就是“嵌入式资源”,但我对此表示怀疑。
完整例外详细信息:
用户代码未处理System.ArgumentException
的HResult = -2147024809
消息=值不在预期范围内。
来源= Windows.Data.Xml.Dom
堆栈跟踪:
在Windows.Data.Xml.Dom.XmlDocument.LoadFromUriAsync(Uri uri,XmlLoadSettings loadSettings)
在D:\ Projects \ Crystal \ library \ IO \ File \ XmlFileSerializer.cs中的Crystal.IO.File.XmlFileSerializer.d__1.MoveNext():第32行
的InnerException:
下载可能的最小示例来重现问题: test_xml.zip
在我查看Windows Runtime Xml数据API示例后,我终于明白了。
public override async Load() { var file = await GetPackagedFile("assets", "world.xml"); LoadXml(file); } private async void LoadXml(StorageFile file) { XmlLoadSettings settings = new XmlLoadSettings() { ValidateOnParse = false }; XmlDocument xmlDoc = await XmlDocument.LoadFromFileAsync(file, settings); foreach (IXmlNode xmlNode in xmlDoc.ChildNodes) { //ProcessNode(xmlNode); } } private async Task GetPackagedFile(string folderName, string fileName) { StorageFolder installFolder = Windows.ApplicationModel.Package.Current.InstalledLocation; if (folderName != null) { StorageFolder subFolder = await installFolder.GetFolderAsync(folderName); return await subFolder.GetFileAsync(fileName); } else { return await installFolder.GetFileAsync(fileName); } } }