使用自定义类型扩展指定 DataTemplate.DataType

2023-11-24

我有这个标记扩展

public class NullableExtension : TypeExtension
{
    public NullableExtension() {
    }

    public NullableExtension( string type )
        : base(type) {
    }

    public NullableExtension( Type type )
        : base(type) {
    }

    public override object ProvideValue( IServiceProvider serviceProvider ) {
        Type basis = (Type)base.ProvideValue( serviceProvider );
        return typeof(Nullable<>).MakeGenericType( basis );
    }
}

它旨在提供某些其他类型的可为空版本。在“正常”XAML 中使用时,它可以按预期工作。例如,如

<SomeControl DataContext="{My:Nullable System:Int32}"/>

(假设 My 是为保存扩展的 C# 命名空间定义的 XML 命名空间,对于 System 也类似)。控件的数据上下文被设置为System.Type for Nullable<int>正如我所期望的。

但是,当我使用此扩展尝试设置DataType的财产DataTemplate like

<DataTemplate DataType="{My:Nullable System:Int32}">
  <TextBlock ... />
</DataTemplate>

编译器告诉我,

字典的键不能是类型 'System.Windows.Controls.Primitives.TextBlock'。只有字符串, 支持 TypeExtension 和 StaticExtension。”

and

“‘NullableExtension’类型的构造函数没有 1 个参数。

有谁知道为什么只有这三种方法(甚至不是TypeExtension,就像我的一样)被允许吗?此时 XAML 的处理有何特别之处?是否有另一种方法可以实现此目的(基于可能可为空的类型选择数据模板),而无需求助于DataTemplateSelector?


我真的很了解你的问题,这就是我的发现。

Q:为什么只有这三个(String, TypeExtension, and StaticExtension) 被允许?

A:通过设计。如果您可以编写任何自定义标记扩展来用作字典中的键,这会带来什么副作用?考虑您将 Bi​​nding 作为 DataType 的值...我很确定您可以添加与字典键动态性质相关的许多问题。

Q:此时 XAML 的处理有何特别之处?

A。此时您已创建 BAML。问题来自内部类BamlRecordWriter,但该消息并未描述实际问题。当您指定自定义标记扩展作为 DataType 时,它​​采用 DataTemplate 的child,并检查它是否可以从 string、TypeExtension 或 StaticExtension 分配(请参阅BamlRecordWriter.WriteElementStart()功能)。的确。不是您的扩展(可分配给 TypeExtension),而是第一个子扩展(不可分配)。现在你有这个奇怪的“不能是类型虽然它看起来像 BamlRecordWriter 的 bug,但我认为他们是故意留下的。除非它不允许您使用自定义标记扩展作为 DataType 值,否则谁会关心错误消息呢?

Q:是否有另一种方法可以实现此目的(基于可能可为空的类型选择数据模板),而无需求助于 DataTemplateSelector?

A:是的,有点。首先,您可以让标准 TypeExtension 为您完成所有脏活:

<DataTemplate DataType="{x:Type TypeName=System:Nullable`1[[System.Int32]]}">
</DataTemplate>

但在大多数情况下(如果不是总是)您将看不到模板结果。为什么?现在涉及可为空类型的装箱规则。对非 null 可为 null 的值类型进行装箱是对值类型本身进行装箱,而不是对包装该值类型的 System.Nullable 进行装箱。因此,默认模板选择器将查找 DataTemplate 的 DataType 为T not of Nullable<T>.

我可能不明白您试图使用可为空扩展解决的确切问题,但您可能希望将可为空包装到您自己的引用类型中,为包装器编写一个 DataTemplate 并使用DataTemplate.Triggers,选择内容外观。好吧,这看起来像是重新发明的数据模板选择器:)...

NB: I'm not a MS guy, and my findings are based on Reflector and my own experience (which is not as big as I would like it to be alt text ). In any case, hope I could help :).

Cheers

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

使用自定义类型扩展指定 DataTemplate.DataType 的相关文章

随机推荐

  • 将 NSTextField 绑定到 NSNumber

    我正在尝试使用 NSTextField 进行整数用户输入 文本字段绑定到 NSNumber 属性 在 setter 方法中 我清理输入值 确保它是 int 并在必要时设置该属性 我发送了 willChangeValueForKey 和 di
  • 如果条件不成立则防止违约

    我有一个链接 当有人点击它时 我想在让它工作之前检查一些条件 如果它是false应防止默认操作 pager next a active click function event if a 1 event preventDefault 该链接
  • 核心数据ios9:多字段唯一约束

    我知道核心数据的新功能是独特的约束 所以我决定测试它 我创建了简单的模式 当我为一个字段 例如名字 添加约束时 一切正常 如果我为另一个字段 姓氏 添加约束 核心数据分别为每个字段创建两个不同的约束 我尝试在一行中添加两个以逗号分隔的字段
  • JBehave 在场景期间跨步骤 Give/When/Then 维护数据

    我已经尝试 JBehave 一段时间了 我需要弄清楚是否存在一种方法可以在一个特定场景的运行期间跨步骤维护数据 我的意思是 是否可以在给定 何时 然后的场景中维护状态 数据 而不使用 Step Class 下的任何状态变量 是的 您可以将维
  • 在正则表达式javascript中转义问号

    我认为这是一个简单的问题 我正在尝试使用 JavaScript 中的正则表达式来搜索一个字符串在另一个字符串中的出现 如下所示 var content Hi I like your Apartment Could we schedule a
  • 使用 php 从字符串中查找文件名

    public images portfolio i vis 1 jpg 无论使用 php 的文件名是什么 我如何删除所有路径 看一下basename path public images portfolio i vis 1 jpg name
  • 耶拿从乌龟读取失败

    我刚刚将 jena 库导入到 eclipse 中以处理 rdf s 这是我的第一次尝试 但我无法读取海龟 ttl 文件 我按照以下方式尝试过 import java io import java util import com hp hpl
  • 没有final修饰符的按需初始化持有者惯用语线程安全吗

    我有预感 使用holder 习惯用法而不将holder 字段声明为final 不是线程安全的 由于Java 中不变性的工作方式 有人可以证实这一点吗 希望有一些消息来源 public class Something private long
  • 引用类型中定义的值类型存储在哪里(堆或堆栈)?

    引用类型中定义的值类型是存储在堆上还是堆栈上 如果存储在堆上 那么什么时候值类型存储在堆栈上 如果存储在堆栈上 那么当所有内容最终都以值类型结束时 堆内会存放什么 存储在堆栈上的唯一变量是函数的局部变量 对于引用类型 引用存储在堆栈上 而它
  • 如何更改 VS Code 的“资源管理器”窗口中的字体?

    有没有办法更改资源管理器窗口 左侧面板显示工作目录中的文件 而不是您编写代码的编辑器 中的字体 实际上有一个扩大在 vscode 中提供所需的功能 按照链接中的说明进行操作 添加CSS代码 monaco panel view in vsco
  • 检测postMessage是否可以发送对象?

    我正在寻找一种巧妙的方法来检测浏览器中的 postMessage 是否支持对象或字符串的发送和接收 我认为肯定有人写过一些这样做的东西 但我还没有找到解决方案 我正在使用 postMessage 向 WebWorker 发送数据 从 Web
  • Xcode 12 和 iOS 14 中的手势问题

    升级到 Xcode 12 和 iOS 14 后遇到问题 设想 我有一个嵌套的 UITableView 嵌套表视图 像下面这样 class GAllowGestureEventPassTableView UITableView UIGestu
  • new 和 new[1] 和有什么区别?

    有什么区别new and new 1 我可以用吗delete with new 1 Edit 好吧好吧 我应该提供背景 对此感到抱歉 我正在使用 VS 2010 评估 BoundsChecker 当我在 new 1 上使用 delete 时
  • 查找 int 的“字符串长度”

    基本上我想返回 int gt 值中的位数 如下所示 int 1 gt 1 int 123 gt 3 int 12345678 gt 8 我对C一无所知 所以请耐心等待 我知道 Objective C 但我使用整数和浮点数而不是 NSNumb
  • 如何将csv中的数据获取到python对象中

    我是一个Python初学者 无法以所需的对象格式将数据从 csv 导入 python 以满足 python 函数的要求 如果我在 python 中手动创建数据 而不是从 csv 引入数据 则以下代码有效 class Student obje
  • ggplot2:手动添加图例

    我怎样才能绘制地图any现有 ggplot 的 不相关 图例 免责声明 请不要恨我 我知道使用 ggplot2 创建图例的最佳方法是正确映射数据 99 的情况下我都会这样做 然而 我在这里要求的东西通常可以给我任何我想要的传奇 As an
  • 如何使用 Ninject 实例化 MEF 导出对象?

    我的应用程序正在使用 MEF 从外部程序集中导出一些类 这些类是为构造函数注入而设置的 我面临的问题是 当我尝试访问这些类时 MEF 正在尝试实例化这些类 有没有办法让 Ninject 负责类的实例化 IEnumerable
  • Java 中带有整数键的哈希表

    我正在尝试创建一个哈希表 如下所示 Hashtable
  • 将 T-SQL 语句解析为标记

    你可以看到here多好啊C 代码语句被解析为标记 例如 以下代码 namespace MyNamespace class MyClass public void MyFunction int arg1 int var1 arg1 被解析为
  • 使用自定义类型扩展指定 DataTemplate.DataType

    我有这个标记扩展 public class NullableExtension TypeExtension public NullableExtension public NullableExtension string type base