当前位置: 首页 > news >正文

【WPF.NET开发】预览事件

本文内容

  1. 先决条件
  2. 预览标记为“已处理”的事件
  3. 通过控件解决事件禁止问题

预览事件,也称为隧道事件,是从应用程序根元素向下遍历元素树到引发事件的元素的路由事件。 引发事件的元素在事件数据中报告为Source
。 并非所有事件场景都支持或需要预览事件。 本文介绍了预览事件存在的位置以及应用程序或组件如何与其交互。

1、先决条件

本文假定你对路由事件有基本的了解,并且已阅读路由事件概述
。 若要遵循本文中的示例,如果熟悉 Extensible Application Markup Language (XAML) 并知道如何编写 Windows Presentation Foundation (WPF) 应用程序,将会很有帮助。

2、预览标记为“已处理”的事件

在事件数据中将预览事件标记为“已处理”时要谨慎。 将预览事件标记为已在引发该事件的元素之外的其他元素上处理,可阻止引发该事件的元素处理该事件。 有时,将预览事件标记为“已处理”是有意的。 例如,复合控件可能会禁止由单个组件引发的事件,并将它们替换为由完整控件引发的事件。 控件的自定义事件可以根据组件状态关系提供自定义的事件数据和触发器。

对于
输入事件,事件数据由每个事件的预览和非预览(浮升)等效项共享。 如果使用预览事件类处理程序将输入事件标记为“已处理”,则通常不会调用浮升输入事件的类处理程序。 或者,如果使用预览事件实例处理程序将事件标记为“已处理”,则通常不会调用浮升输入事件的实例处理程序。 尽管即使将事件标记为“已处理”,你也可以配置要调用的类和实例处理程序,但该处理程序配置并不常见。

并非所有预览事件都是隧道
事件。 例如,PreviewMouseLeftButtonDown 输入事件通过元素树跟踪向下路由,但它是由路径中的每个 UIElement 引发和重新引发的
直接路由事件。

3、通过控件解决事件禁止问题

一些复合控件在组件级别禁止输入事件,以便将其替换为自定义的高级事件。 例如,WPF ButtonBase 将 MouseLeftButtonDown 浮升输入事件标记为在其 OnMouseLeftButtonDown 方法中处理并引发 Click 事件。 MouseLeftButtonDown 事件及其事件数据仍沿元素树路径继续,但由于该事件在事件数据中标记为 Handled,因此将仅调用配置为响应“已处理”事件的处理程序。

如果希望由应用程序根目录的其他元素处理标记为“已处理”的路由事件,则可以执行以下操作:

  • 通过调用 UIElement.AddHandler(RoutedEvent, Delegate, Boolean) 方法并将参数 handledEventsToo 设置为 true 来附加处理程序。 此方法需要在获取要附加到的元素的对象引用后,在代码隐藏中附加事件处理程序。

  • 如果标记为“已处理”的事件是浮升事件,则附加等效预览事件的处理程序(如果可用)。 例如,如果控件禁止了 MouseLeftButtonDown 事件,则可以改为附加 PreviewMouseLeftButtonDown 事件的处理程序。 此方法仅适用于实现
    隧道和
    浮升路由策略并共享事件数据的基元素输入事件。

以下示例实现了一个名为 componentWrapper 的基本自定义控件,其中包含一个 TextBox。 控件被添加到名为 outerStackPanel 的 StackPanel。

<StackPanel Name="outerStackPanel"VerticalAlignment="Center"custom:ComponentWrapper.CustomKey="Handler_PrintEventInfo"TextBox.KeyDown="Handler_PrintEventInfo"TextBox.PreviewKeyDown="Handler_PrintEventInfo" ><custom:ComponentWrapperx:Name="componentWrapper"TextBox.KeyDown="ComponentWrapper_KeyDown"custom:ComponentWrapper.CustomKey="Handler_PrintEventInfo"HorizontalAlignment="Center"><TextBox Name="componentTextBox" Width="200" KeyDown="Handler_PrintEventInfo" /></custom:ComponentWrapper>
</StackPanel>

每当发生击键操作时,componentWrapper 控件都会侦听由其 TextBox 组件引发的 KeyDown 浮升事件。 在这种情况下,componentWrapper 控件:

  1. 将 KeyDown 浮升路由事件标记为“已处理”以禁止该事件。 因此,只会触发在代码隐藏中配置为响应“已处理”KeyDown 事件的 outerStackPanel 处理程序。 不会调用在 XAML 中为 KeyDown 事件附加的 outerStackPanel 处理程序。

  2. 引发名为 CustomKey 的自定义浮升路由事件,该事件触发 CustomKey 事件的 outerStackPanel 处理程序。

public partial class MainWindow : Window
{public MainWindow(){InitializeComponent();// Attach a handler on outerStackPanel that will be invoked by handled KeyDown events.outerStackPanel.AddHandler(KeyDownEvent, new RoutedEventHandler(Handler_PrintEventInfo), handledEventsToo: true);}private void ComponentWrapper_KeyDown(object sender, System.Windows.Input.KeyEventArgs e){Handler_PrintEventInfo(sender, e);Debug.WriteLine("KeyDown event marked as handled on componentWrapper.\r\n" +"CustomKey event raised on componentWrapper.");// Mark the event as handled.e.Handled = true;// Raise the custom click event.componentWrapper.RaiseCustomRoutedEvent();}private void Handler_PrintEventInfo(object sender, System.Windows.Input.KeyEventArgs e){string senderName = ((FrameworkElement)sender).Name;string sourceName = ((FrameworkElement)e.Source).Name;string eventName = e.RoutedEvent.Name;string handledEventsToo = e.Handled ? " Parameter handledEventsToo set to true." : "";Debug.WriteLine($"Handler attached to {senderName} " +$"triggered by {eventName} event raised on {sourceName}.{handledEventsToo}");}private void Handler_PrintEventInfo(object sender, RoutedEventArgs e){string senderName = ((FrameworkElement)sender).Name;string sourceName = ((FrameworkElement)e.Source).Name;string eventName = e.RoutedEvent.Name;string handledEventsToo = e.Handled ? " Parameter handledEventsToo set to true." : "";Debug.WriteLine($"Handler attached to {senderName} " +$"triggered by {eventName} event raised on {sourceName}.{handledEventsToo}");}// Debug output://// Handler attached to outerStackPanel triggered by PreviewKeyDown event raised on componentTextBox.// Handler attached to componentTextBox triggered by KeyDown event raised on componentTextBox.// Handler attached to componentWrapper triggered by KeyDown event raised on componentTextBox.// KeyDown event marked as handled on componentWrapper.// CustomKey event raised on componentWrapper.// Handler attached to componentWrapper triggered by CustomKey event raised on componentWrapper.// Handler attached to outerStackPanel triggered by CustomKey event raised on componentWrapper.// Handler attached to outerStackPanel triggered by KeyDown event raised on componentTextBox. Parameter handledEventsToo set to true.
}public class ComponentWrapper : StackPanel
{// Register a custom routed event using the Bubble routing strategy.public static readonly RoutedEvent CustomKeyEvent = EventManager.RegisterRoutedEvent(name: "CustomKey",routingStrategy: RoutingStrategy.Bubble,handlerType: typeof(RoutedEventHandler),ownerType: typeof(ComponentWrapper));// Provide CLR accessors for assigning an event handler.public event RoutedEventHandler CustomKey{add { AddHandler(CustomKeyEvent, value); }remove { RemoveHandler(CustomKeyEvent, value); }}public void RaiseCustomRoutedEvent(){// Create a RoutedEventArgs instance.RoutedEventArgs routedEventArgs = new(routedEvent: CustomKeyEvent);// Raise the event, which will bubble up through the element tree.RaiseEvent(routedEventArgs);}
}

该示例演示了两种解决方法,用于获取禁止的 KeyDown 路由事件以调用附加到 outerStackPanel 的事件处理程序:

  • 将 PreviewKeyDown 事件处理程序附加到 outerStackPanel。 由于预览输入路由事件先于等效的浮升路由事件,因此示例中的 PreviewKeyDown 处理程序在 KeyDown 处理程序之前运行,后者通过共享事件数据禁止预览和浮升事件。

  • 使用代码隐藏中的 UIElement.AddHandler(RoutedEvent, Delegate, Boolean) 方法将 KeyDown 事件处理程序附加到 outerStackPanel,并将 handledEventsToo 参数设置为 true

 备注

将输入事件的预览或非预览等效项标记为“已处理”都是禁止控件组件引发的事件的策略。 使用的方法取决于应用程序要求。

相关文章:

【WPF.NET开发】预览事件

本文内容 先决条件预览标记为“已处理”的事件通过控件解决事件禁止问题 预览事件&#xff0c;也称为隧道事件&#xff0c;是从应用程序根元素向下遍历元素树到引发事件的元素的路由事件。 引发事件的元素在事件数据中报告为Source 。 并非所有事件场景都支持或需要预览事件。…...

JDBC->SpringJDBC->Mybatis封装JDBC

一、JDBC介绍 Java数据库连接&#xff0c;&#xff08;Java Database Connectivity&#xff0c;简称JDBC&#xff09;是Java语言中用来规范客户端程序如何来访问数据库的应用程序接口&#xff0c;提供了诸如查询和更新数据库中数据的方法。JDBC也是Sun Microsystems的商标。我们…...

ts中的keyof 关键字

const getVal <T,K extends keyof T>(obj:T,key:K) : T[K]>{return obj[key]; }使用了 keyof 关键字。keyof 是 TypeScript 的一个特性&#xff0c;它返回一个字符串字面量类型&#xff0c;表示对象类型的所有属性键的联合类型。 这段代码定义了一个泛型函数 gatVal&…...

Head First Design Patterns - 装饰者模式

什么是装饰者模式 装饰者模式动态地将额外责任附加到对象上。对于拓展功能&#xff0c;装饰者提供子类化的弹性替代方案。 --《Head First Design Patterns》中的定义 为什么会有装饰者模式 根据上述定义&#xff0c;简单来说&#xff0c;装饰者模式就是对原有的类&#xff0c…...

MySQL 执行过程

MySQL 的执行流程也确实是一个复杂的过程&#xff0c;它涉及多个组件的协同工作&#xff0c;故而在面试或者工作的过程中很容易陷入迷惑和误区。 MySQL 执行过程 本篇将以 MySQL 常见的 InnoDB 存储引擎为例&#xff0c;为大家详细介绍 SQL 语句的执行流程。从连接器开始&…...

判断电话号码是否重复-excel

有时候重复的数据不需要或者很烦人&#xff0c;就需要采取措施&#xff0c;希望以下的方法能帮到你。 1.判断是否重复 方法一&#xff1a; 1&#xff09;针对第一个单元格输入等号&#xff0c;以及公式countif(查找记录数的范围&#xff0c;需要查找的单元格&#xff09; 2…...

【Java开发岗面试】八股文—Java虚拟机(JVM)

声明&#xff1a; 背景&#xff1a;本人为24届双非硕校招生&#xff0c;已经完整经历了一次秋招&#xff0c;拿到了三个offer。本专题旨在分享自己的一些Java开发岗面试经验&#xff08;主要是校招&#xff09;&#xff0c;包括我自己总结的八股文、算法、项目介绍、HR面和面试…...

【Linux】Linux 下基本指令 -- 详解

无论是什么命令&#xff0c;用于什么用途&#xff0c;在 Linux 中&#xff0c;命令有其通用的格式&#xff1a; command [-options] [parameter] command&#xff1a;命令本身。-options&#xff1a;[可选&#xff0c;非必填]命令的一些选项&#xff0c;可以通过选项控制命令的…...

Eureka注册及使用

一、Eureka的作用 Eureka是一个服务注册与发现的工具&#xff0c;主要用于微服务架构中的服务发现和负载均衡。其主要作用包括&#xff1a; 服务提供者将自己注册到Eureka Server上&#xff0c;包括服务的地址和端口等信息。服务消费者从Eureka Server上获取服务提供者的地址…...

Ubuntu之修改时区/时间

1、查看当前时间及时区状态 sudo timedatectl status # 显示当前时区为Asia/Shanghai 2、查看当前系统时间 sudo date 3、查看当前系统时间及时区 sudo date -R # 显示当前时间及对应时区&#xff0c;时区为“0800”北京时区 4、修改硬件时间 修改日期格式&#xff1a…...

4、内存泄漏检测(多线程)

4、内存泄漏多线程 多线程下使用Valgrind 工具的memcheck检查. 安装 sudo apt install valgrind使用 valgrind --toolmemcheck --leak-checkfull ./app_main 指令效果如下所示. wqwq-Virtual-Machine:~/work/test_zlog/build$ valgrind --toolmemcheck --leak-checkfull .…...

在使用tcp长连接时,是否还需要再引入重发机制?

一 什么是tcp长连接&#xff1f; 在TCP&#xff08;Transmission Control Protocol&#xff09;中&#xff0c;长连接是指在通信过程中保持连接状态的一种方式&#xff0c;相对于短连接而言。长连接通常用于需要频繁通信的场景&#xff0c;以减少连接建立和断开的开销。在长连接…...

记一次Oracle Cloud计算实例ssh恢复过程

#ssh秘钥丢失# &#xff0c; #Oracle Cloud# 。 电脑上的ssh秘钥文件不知道什么时候丢失了&#xff0c;直到用的时候才发现没有了&#xff0c;这下可好&#xff0c;Oracle Cloud的计算实例连不上了&#xff0c;这个实例只能通过ssh连接上去&#xff1a; 以下是解决步骤&#x…...

2024年01月数据库流行度最新排名

点击查看最新数据库流行度最新排名&#xff08;每月更新&#xff09; 2024年01月数据库流行度最新排名 TOP DB顶级数据库索引是通过分析在谷歌上搜索数据库名称的频率来创建的 一个数据库被搜索的次数越多&#xff0c;这个数据库就被认为越受欢迎。这是一个领先指标。原始数…...

Stable Diffusion API入门:简明教程

Stable Diffusion 是一个先进的深度学习模型&#xff0c;用于创造和修改图像。这个模型能够基于文本描述来生成图像&#xff0c;让机器理解和实现用户的创意。使用这项技术的关键在于掌握其 API&#xff0c;通过编程来操控图像生成的过程。 在探索 Stable Diffusion API 的世界…...

数据结构--二叉搜索树的实现

目录 1.二叉搜索树的概念 2.二叉搜索树的操作 二叉搜索树的插入 中序遍历(常用于排序) 二叉搜索树的查找 二叉搜索树的删除 完整二叉树代码&#xff1a; 二叉搜索树的应用 key/value搜索模型整体代码 1.二叉搜索树的概念 二叉搜索树又称二叉排序树&#xff0c;它或者是一…...

《微信小程序开发从入门到实战》学习六十八

6.6 网络API 6.6.1 网络API 使用wx.request接口可以发起网络请求。该接口接受一个Object参&#xff0c;参数支持属性如下所示&#xff1a; url(必填)&#xff1a;开发者服务器地址 data&#xff1a;请求的参数&#xff0c;类型为string/object/ArrayBuffer header&#xf…...

阿里是如何去“O”的?

大家好&#xff0c;我是老猫&#xff0c;猫头鹰的“猫”。 今天我们来聊聊数据库这个话题。 2009年&#xff0c;阿里提出“去IOE化”的概念&#xff0c;这在当时看起来是天方夜谭&#xff0c;但目前来看可以说是"轻舟已过万重山"。 IOE是传统IT三大件&#xff0c;…...

蓝桥杯备赛 day 1 —— 递归 、递归、枚举算法(C/C++,零基础,配图)

目录 &#x1f308;前言 &#x1f4c1; 枚举的概念 &#x1f4c1;递归的概念 例题&#xff1a; 1. 递归实现指数型枚举 2. 递归实现排列型枚举 3. 递归实现组合型枚举 &#x1f4c1; 递推的概念 例题&#xff1a; 斐波那契数列 &#x1f4c1;习题 1. 带分数 2. 反硬币 3. 费解的…...

87 双指针解验证回文字符串II

问题描述&#xff1a;简单给定一个非空字符串s&#xff0c;最多删除一个字符&#xff0c;判断是否成为回文字符串。 双指针解法&#xff1a;指针1指向开头&#xff0c;指针2指向结尾&#xff0c;定义一个count记录不满足回文串的数量&#xff0c;若超过1&#xff0c;则返回fal…...

Cogito-V1-Preview-Llama-3B开发:微信小程序智能客服对接实战

Cogito-V1-Preview-Llama-3B开发&#xff1a;微信小程序智能客服对接实战 最近有不少朋友在问&#xff0c;把大模型部署到服务器上之后&#xff0c;怎么才能让微信小程序用起来&#xff1f;今天我就以星图GPU平台上部署的Cogito-V1-Preview-Llama-3B模型为例&#xff0c;跟大家…...

Windows系统下Tesseract OCR与Python结合实战:从安装到文字识别应用

1. Windows系统下Tesseract OCR的安装与配置 第一次接触OCR技术时&#xff0c;我被它的神奇能力震撼到了——居然能让计算机读懂图片里的文字&#xff01;作为一款开源OCR引擎&#xff0c;Tesseract在文字识别领域已经默默耕耘了十几年。记得我刚开始用的时候还是3.x版本&#…...

别再只升级OpenSSH了!一次搞懂Linux离线环境下的依赖包管理与编译安装避坑指南

离线环境下的Linux软件编译&#xff1a;从OpenSSH升级到通用依赖管理方法论 当你面对一台无法连接互联网的Linux服务器时&#xff0c;软件升级和安装往往会变成一场噩梦。想象一下&#xff1a;你下载了最新版OpenSSH的源码包&#xff0c;满怀希望地执行./configure&#xff0c;…...

dbg-macro配置完全指南:禁用宏、强制颜色输出与警告控制

dbg-macro配置完全指南&#xff1a;禁用宏、强制颜色输出与警告控制 【免费下载链接】dbg-macro A dbg(…) macro for C 项目地址: https://gitcode.com/gh_mirrors/db/dbg-macro dbg-macro是一款轻量级C调试宏工具&#xff0c;通过简单的dbg(...)语法即可实现变量值、类…...

墨语灵犀开源模型生态:对接LangChain/RAG构建专属翻译知识库

墨语灵犀开源模型生态&#xff1a;对接LangChain/RAG构建专属翻译知识库 1. 引言&#xff1a;当古典美学遇见现代AI架构 在人工智能技术快速发展的今天&#xff0c;翻译工具已经从简单的词汇转换演变为理解文化语境和语义深度的智能系统。「墨语灵犀」作为基于腾讯混元大模型…...

OpenClaw成本优化方案:自建Qwen3-VL:30B替代高价多模态API

OpenClaw成本优化方案&#xff1a;自建Qwen3-VL:30B替代高价多模态API 1. 为什么需要关注OpenClaw的成本问题 第一次用OpenClaw完成多模态任务时&#xff0c;我被账单吓了一跳。当时需要处理200张产品图片的分类和描述生成&#xff0c;调用某商业多模态API后&#xff0c;费用…...

OpenClaw技能分享:GLM-4.7-Flash驱动的邮件自动处理系统

OpenClaw技能分享&#xff1a;GLM-4.7-Flash驱动的邮件自动处理系统 1. 为什么需要自动化邮件处理 每天早晨打开邮箱&#xff0c;看到堆积如山的未读邮件总让人头皮发麻。作为一个小团队的负责人&#xff0c;我经常需要处理客户咨询、内部沟通、会议邀请等各种类型的邮件。最…...

5个核心功能提升音频处理效率:AsrTools语音转文字工具用户指南

5个核心功能提升音频处理效率&#xff1a;AsrTools语音转文字工具用户指南 【免费下载链接】AsrTools ✨ AsrTools: Smart Voice-to-Text Tool | Efficient Batch Processing | User-Friendly Interface | No GPU Required | Supports SRT/TXT Output | Turn your audio into a…...

STM32智能甲鱼养殖系统设计与实现

基于STM32的智能甲鱼养殖系统设计与实现1. 项目概述1.1 系统背景现代水产养殖行业正面临从传统人工管理向智能化转型的关键时期。甲鱼作为对水质环境敏感的特种水产品&#xff0c;其养殖过程中需要持续监测多项水质参数并保持稳定环境。传统人工监测方式存在响应滞后、精度不足…...

正点原子IMX6ULL史诗级新内核Linux7.0移植教程(5)梭哈配置主线设备树

正点原子IMX6ULL史诗级新内核Linux7.0移植教程&#xff08;5&#xff09;梭哈配置主线设备树 仓库已经开源&#xff0c;可以研究补丁和直接看完整教程&#xff1a;https://github.com/Awesome-Embedded-Learning-Studio/imx-forge 有任何意见欢迎提出 PR&#xff01;会第一时间…...