Silverlight实现ComboGrid功能
Silverlight带了Combox控件,但这个控件只能选择不能编辑,虽然它能定义Item外观,但如果下拉选择是一个DataGrid控件似乎就不好定义了.还好Silverlight提供了一个灵活的Popup控件,通过它能实现类似于ComboGrid的功能.
先看一下需要的功能效果:
我们需要在选择项后自动地把选择的数据填充到相关性的两个TextBox中.实现这个功能我们选择了TextBox,Button和一个自定义的Popup DataGrid用户控件.由于Popup只负责显示但我们需要解决一些总是,就是当Popup显示的时候点击自身或其他区域就自动关闭,所以需用要把Popup DataGrid封装一起方便处理.
以下是这个Popup DataGrid的实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | < UserControl x:Class="ComboGrid.ComboGrid" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d" d:DesignHeight="300" d:DesignWidth="400" xmlns:sdk="http://schemas.microsoft.com/winfx/2006/xaml/presentation/sdk" Loaded="UserControl_Loaded"> < Grid x:Name="LayoutRoot" Background="#09FFFFFF" MouseRightButtonDown="LayoutRoot_MouseRightButtonDown" MouseLeftButtonDown="LayoutRoot_MouseLeftButtonDown"> < sdk:DataGrid AutoGenerateColumns="False" HorizontalAlignment="Left" Name="dataGrid1" VerticalAlignment="Top" Width="253" MouseLeftButtonDown="dataGrid1_MouseLeftButtonDown" SelectionChanged="dataGrid1_SelectionChanged"> < sdk:DataGrid.Columns > < sdk:DataGridTextColumn Binding="{Binding Name}" CanUserReorder="True" CanUserResize="True" CanUserSort="True" Width="120" Header="Name" /> < sdk:DataGridTextColumn Binding="{Binding Host}" CanUserReorder="True" CanUserResize="True" CanUserSort="True" Width="*" Header="Host" /> </ sdk:DataGrid.Columns > </ sdk:DataGrid > </ Grid > </ UserControl > |
LayoutRoot的背景设置非常重要,因为我们需要用它来做这遮罩,来捕获DataGrid周边的鼠标点击事件,为了不影响整个布局的外观好尽可能的设置接近秀明.给用户控件定义两个mouse down事件自动隐藏
1 2 3 4 5 6 7 8 9 | private void LayoutRoot_MouseRightButtonDown( object sender, MouseButtonEventArgs e) { Hide(); } private void LayoutRoot_MouseLeftButtonDown( object sender, MouseButtonEventArgs e) { Hide(); } |
为了让DataGrid排序等操作不触这两个事件,需要在DataGrid的LeftMouseDown设置一个属性值
1 2 3 4 | private void dataGrid1_MouseLeftButtonDown( object sender, MouseButtonEventArgs e) { e.Handled = true ; } |
这样DataGrid点击鼠标左键的时候就不会把Popup隐藏了.下面是给控件定义显示方法.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | public void Show(Control target,Point Offset) { mPopup = new Popup(); this .Width = Application.Current.Host.Content.ActualWidth; this .Height = Application.Current.Host.Content.ActualHeight; GeneralTransform gt = target.TransformToVisual(Application.Current.RootVisual as UIElement); Point offset = gt.Transform( new Point(0, 0)); double controlTop = offset.Y; double controlLeft = offset.X; Point postion= new Point(controlLeft + Offset.X, controlTop + Offset.Y); mPopup.Child = this ; dataGrid1.Margin = new Thickness(postion.X, postion.Y, 0, 0); mPopup.IsOpen = true ; } |
方法带两个参数,第一个是目标控件,是指Popup的位置就显示在这个控件之上,第二个方法就是偏移座标.最终通过修改DataGrid的Margin来达到所需位置的显示.控件隐藏方法代码相对也是非常简单
1 2 3 4 5 6 7 8 9 10 | public void Hide() { if (mPopup != null ) { mPopup.IsOpen = false ; mPopup.Child = null ; mPopup = null ; } } |
下面的工作就是处理DataGrid的SelectChanged需要做的事件,当我们改变选择项的同时触发一个事件告诉调用者和把当前Popup关闭即可.
1 2 3 4 5 6 7 8 9 | private void dataGrid1_SelectionChanged( object sender, SelectionChangedEventArgs e) { if (dataGrid1.SelectedItem != null ) { Hide(); if (Selected != null ) Selected((UserData)dataGrid1.SelectedItem); } } |
到这时Popup DataGrid的就已经封装完成,那实际调用代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 | private ComboGrid mComboGrid = new ComboGrid(); private void button1_Click( object sender, RoutedEventArgs e) { mComboGrid.Show(textBox1, new Point(0, 26)); } private void UserControl_Loaded( object sender, RoutedEventArgs e) { mComboGrid.Selected += (s) => { textBox1.Text = s.Name; textBox2.Text = s.Host; }; } |
Silverlight提供给我们的Popup可以实现的功能有很多,MessageBox,自定义Combox和右键菜单等等.迟下会讲解如何实现一个右键菜单.
以下这个地址实现了这几种效果:sl.henryfan.net
下载完整代码: ComboGrid.rar (1.88 mb)
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系统下SQL Server数据库镜像配置全流程详解
· 现代计算机视觉入门之:什么是视频
· 你所不知道的 C/C++ 宏知识
· 聊一聊 操作系统蓝屏 c0000102 的故障分析
· SQL Server 内存占用高分析
· DeepSeek V3 两周使用总结
· 回顾我的软件开发经历(1)
· C#使用yield关键字提升迭代性能与效率
· 低成本高可用方案!Linux系统下SQL Server数据库镜像配置全流程详解
· 4. 使用sql查询excel内容