XAMLServices 类和基本的 XAML 读取或写入

XamlServices 是 .NET Framework XAML 服务提供的一个类,该类可用于满足特定 XAML 方案的需求,这些方案不需要对 XAML 节点流或从那些节点获得的 XAML 类型系统信息的特定访问。 XamlServices API 可总结为:用于支持 XAML 加载路径的 Load 或 Parse、用于支持 XAML 保存路径的 Save 以及用于提供联接加载路径和保存路径的方法的 Transform。 Transform 可用于从一个 XAML 架构更改为另一个架构。 本主题概述每个 API 分类并介绍特定方法重载之间的区别。

本主题包括下列各节。

  • 加载
  • Parse
  • 保存
  • 变换
  • 相关主题

加载

Load 的各种重载实现加载路径的完整逻辑。 加载路径以某种形式使用 XAML 并输出 XAML 节点流。 这些加载路径中的大多数都以编码的 XML 文本文件形式使用 XAML。 但是,您也可以加载常规流,或者可以加载其他 XamlReader 实现中已包含的预加载 XAML 源。

多数方案的最简单重载为 Load(String)。 此重载具有一个 fileName 参数,该参数就是包含要加载的 XAML 的文本文件的名称。 这适用于某些应用程序方案,如以前已将状态或数据序列化到本地计算机的完全信任应用程序。 这对于定义应用程序模型并且想加载一个标准文件(该文件定义应用程序行为、启动 UI 或其他框架定义的使用 XAML 的功能)的框架也非常有用。

Load(Stream) 具有类似方案。 如果您具有要加载的用户选择文件,则此重载可能很有用,因为 Stream 是可以访问文件系统的其他 System.IO API 的常见输出。 或者您也可以通过异步下载或同样提供流的其他网络技术来访问 XAML 源。 (从流或用户选择的源进行加载可能存在安全隐患。 有关更多信息,请参见 XAML 安全注意事项。)

Load(TextReader)Load(XmlReader) 是依赖于 .NET Framework 早期版本格式读取器的重载。 若要使用这些重载,您应已经创建了一个读取器实例并使用它的 Create API 以相关形式(文本或 XML)加载 XAML。 如果您已经在其他读取器中移动了记录指针或对它们执行了其他操作,则这并不重要。 Load 中的加载路径逻辑始终从根目录向下处理整个 XAML 输入。 这些重载的方案可能包括以下几种:

  • 提供现有 XAML 特定文本编辑器中简单 XML 编辑功能的设计图面。

  • 核心 System.IO 方案的变体,其中您可使用专用的读取器打开文件或流。 在尝试作为 XAML 加载之前,该逻辑对内容执行初步检查或处理。

通过使用该读取器的 API 进行加载,可以加载文件或流,或者加载包装您的 XAML 输入的 XmlReaderTextReaderXamlReader

在内部,前面的每个重载最终都为 Load(XmlReader),其中传递的 XmlReader 用来创建新的 XamlXmlReader

为更高级方案提供的 Load 签名是 Load(XamlReader)。 此签名可用于以下情况之一:

  • 您已经定义了自己的 XamlReader 的实现。

  • 需要为 XamlReader 指定设置(这些设置因默认设置而异)。

例如,非默认设置就是设置以下任何内容:AllowProtectedMembersOnRootBaseUriIgnoreUidsOnPropertyElementsLocalAssemblyValuesMustBeStringXamlServices 的默认读取器为 XamlXmlReader。 如果您为设置提供自己的 XamlXmlReader,则下列属性要设置为非默认的 XamlXmlReaderSettingsCloseInputSkipXmlCompatibilityProcessingXmlLangXmlSpacePreserve

Parse

Parse 类似于 Load,因为它是从 XAML 输入创建 XAML 节点流的加载路径 API。 但是,在这种情况下,XAML 输入将直接作为包含要加载的所有 XAML 的字符串提供。 Parse 是更适合于应用程序方案的轻量方法(与框架方案相比)。 有关更多信息,请参见 ParseParse 实际上仅是包装的 Load(XmlReader) 调用,该调用在内部涉及一个 StringReader

保存

Save 的各种重载实现保存路径。 所有 Save 方法都将对象图作为输入,并以流、文件或 XmlWriter/TextWriter 实例的形式生成输出。

输入对象应是某些对象表示形式的根对象。 可以是业务对象的单个根对象、UI 方案中某个页面的对象树的根对象、设计工具的工作编辑图面或者适合于这些方案的其他根对象概念。

在很多情况下,您保存的对象树与使用 Load 或使用由框架/应用程序模型实现的其他 API 加载 XAML 时的原始操作有关。 在对象树中捕获的内容可能有所差别,这是因为状态改变、应用程序捕获用户运行时设置的位置改变、由于应用程序是 XAML 设计图面而对 XAML 的改变等。 不管有没有改变,首先从标记加载 XAML,然后再次保存它并比较这两种 XAML 标记形式的概念有时称为 XAML 的往返表示形式。

保存和序列化以标记形式设置的复杂对象的难点在于,实现无信息丢失的完整表示形式与使 XAML 可读性变差的详细内容之间要达到良好平衡。 此外,XAML 的不同客户对于如何设置该平衡可能有不同的定义或期望。 Save API 表示该平衡的一个定义。 Save API 使用可用的 XAML 架构上下文以及 XamlTypeXamlMember 和其他 XAML 内部函数与 XAML 类型系统概念的基于 CLR 的默认特性来确定保存回标记时可以优化某些 XAML 节点流构造的位置。 例如,XamlServices 保存路径可使用基于 CLR 的默认 XAML 架构上下文来解析对象的 XamlType,确定 XamlType.ContentProperty,然后可在将属性写入该对象的 XAML 内容时省略属性元素标记。

变换

Transform 通过以单个操作的形式链接加载路径和保存路径来转换或变换 XAML。 可以对 XamlReaderXamlWriter 使用不同的架构上下文或不同的后备类型系统,这会影响所得到的 XAML 的转换方式。 这也非常适用于广义的转换操作。

对于依赖于检查 XAML 节点流中每个节点的操作,通常不使用 Transform。 而是需要定义自己的加载路径-保存路径操作系列,并插入自己的逻辑。 在其中一个路径中,在您自己的节点循环中使用 XAML 读取器/XAML 编写器对。 例如,使用 XamlXmlReader 加载初始 XAML 并单步执行节点的后续 Read 调用。 现在,在 XAML 节点流级别操作可以调整各个节点(类型、成员或其他节点)以应用转换或使节点保持原样。 此后将节点发送给 XamlObjectWriter 的相关 Write API 并写出该对象。 有关更多信息,请参见了解 XAML 节点流结构和概念

请参见

参考

XamlObjectWriter

XamlServices

概念

XAML 服务