我一直在寻找事件“Preview ******”的描述,就像每个元素都有事件KeyDown和PreviewKeyDown一样。有什么不同(不是一个是附加事件,一个不是,真正的传统差异和编程方式差异)
在从Control派生的任何类中,你可以覆盖这两个方法.. OnKeyDown和OnPreviewKeyDown,现在我正在编写我的自定义控件,我应该使用哪种方法?两者之间有什么不同。
答案 0 :(得分:115)
来自WPF编程 - Chris Sells和Ian Griffith
除直接事件外, WPF定义了大多数路由事件 对 - 一个隧道和另一个 冒泡。隧道事件名称 总是以'预览'开头,是 首先提出这给了父母 有机会看到它之前的事件 到达孩子。接下来是 冒泡的对应物。多数情况 情况下,你只会处理 冒泡一个。预览会是 通常用于
- 阻止事件(
e.Handled = true
)- 使父母提前做正常事件处理。
e.g。如果UI Tree = Button包含Grid包含Canvas包含Ellipse
点击椭圆会导致(MouseDownButton被Button吃掉而Click会被提升。)
PreviewMouseDownButton
PreviewMouseDownGrid
PreviewMouseDownCanvas
PreviewMouseDownEllipse
MouseDownEllipse
MouseDownCanvas
MouseDownGrid
答案 1 :(得分:8)
我发现此博客条目在描述差异时非常有用:
http://joshsmithonwpf.wordpress.com/2007/06/22/overview-of-routed-events-in-wpf/
您有可视树,当事件发生在树中的元素上时,首先预览事件将从根到达元素(隧道):将在所有这些元素上引发PreviewKeyDown事件,然后是“正常”事件将从元素传播到根(冒泡)。
答案 2 :(得分:3)
基本上,它是同一个事件,但恰好在主赛事之前发生。它们存在,因此您可以监听这些类型的事件,而不会在这些事件发生时干扰控件的正常行为。
例如,当您单击或鼠标输入等按钮时,按钮会执行操作。如果您自己处理这些事件,则必须确保执行相同的操作,否则按钮将不会起作用。预览事件为您提供同一时间线中的事件,而不必担心会弄乱现有功能。
这在处理自定义样式/触发器/控件模板时特别有用。当您开始覆盖控件外观/行为时。
因此,在您的控件中,在OnKeyDown事件中执行您想要的主要工作并保留其他人使用的预览事件,我是如何使用它们的。
答案 3 :(得分:3)
这种差异与路由事件有关,这就是WPF实现其事件处理策略的方式。标准事件名称(即KeyDown等)意味着冒泡路由策略。前面带有“预览”(即PreviewKeyDown等)的那些意味着隧道路由策略。您可以更详细地了解这些策略here。基本上,当调用WPF中的事件时,它首先从可视树中的最顶层元素移动到调用该事件的元素,最后向上返回。在树下的路上,您将遇到PreviewKeyDown事件,在返回路程中,您将按顺序遇到KeyDown事件。