右键菜单
- MouseRightButtonDown与 MouseRightButtonUp方法 : 获取右键点击的事件
- Popup类 : 创建弹出菜单。在 Silverlight 控件的界限之内、现有 Silverlight 内容之上显示内容。
XAML:
<UserControl x:Class="PopupDemo.MainPage"
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">
<Grid x:Name="LayoutRoot" Background="White">
<StackPanel Orientation="Vertical">
<TextBlock x:Name="txbMessage" Text="" Margin="10" HorizontalAlignment="Center"/>
<Border x:Name="brdRightClickZone" Width="300" Height="200" Background="BurlyWood"
CornerRadius="10" BorderThickness="1.0">
<TextBlock Text="右键菜单测试区域:在此区域内尝试右键菜单..." TextWrapping="Wrap" Margin="10"/>
</Border>
</StackPanel>
</Grid>
</UserControl>
xaml.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using System.Windows.Controls.Primitives;
namespace PopupDemo
{
public partial class MainPage : UserControl
{
Popup popup = null;
public MainPage()
{
InitializeComponent();
//注册鼠标按键事件
brdRightClickZone.MouseRightButtonDown += new MouseButtonEventHandler(brdRightClickZone_MouseRightButtonDown);
brdRightClickZone.MouseRightButtonUp+=new MouseButtonEventHandler(brdRightClickZone_MouseRightButtonUp);
}
void brdRightClickZone_MouseRightButtonUp(object sender, MouseButtonEventArgs e)
{
txbMessage.Text = "右键单击事件触发";
//获取当前鼠标位置 GetPosition获取相对于LayoutRoot大窗体的相对位置 左上角为0,0
Point currentMousePosition = e.GetPosition(LayoutRoot);
//弹出框
ShowPopup(currentMousePosition);
}
private void ShowPopup(Point currentMousePosition)
{
//判断当前是否还打开这右键菜单
if (popup != null)
{
//如果打开这右键菜单,则关闭右键菜单,清掉popup菜单
popup.IsOpen = false;
popup = null;
}
//创建一个新的popup对象
popup = CreateContextMenu(currentMousePosition);
popup.IsOpen = true;
}
private Popup CreateContextMenu(Point currentMousePosition)
{
Popup popup = new Popup();
Grid popupGrid = new Grid();
Canvas popupCanvas = new Canvas();
popup.Child = popupGrid;
//左键点击时隐藏popup窗口
popupCanvas.MouseLeftButtonDown += (sender, e) => { HidePopup(); };
//右键点击时候,先明确自己本身要处理这个事件后,在进行隐藏Popup窗口
popupCanvas.MouseRightButtonDown += (sender, e) => { e.Handled = true; HidePopup(); };
popupCanvas.Background = new SolidColorBrush(Colors.Transparent);
//把生成好的canvas添加到grid里
popupGrid.Children.Add(popupCanvas);
//添加要显示在popup里的选项内容
popupGrid.Children.Add(CreateContextMenuItems(currentMousePosition));
//设置popup的高宽
popupGrid.Width = Application.Current.Host.Content.ActualWidth;
popupGrid.Height = Application.Current.Host.Content.ActualHeight;
popupCanvas.Width = popupGrid.Width;
popupCanvas.Height = popupGrid.Height;
return popup;
}
private UIElement CreateContextMenuItems(Point currentMousePosition)
{
string[] contextMenuItemsText = { "Context Menu Item A", "Context Menu Item B", "Context Menu Item C", "Context Menu Item D" };
ListBox lstContextMenu = new ListBox();
//生成TextBlock
foreach (string str in contextMenuItemsText)
{
TextBlock txb = new TextBlock() { Text = str };
//注册点击TextBlock选项的事件
txb.MouseLeftButtonDown += new MouseButtonEventHandler(txb_MouseLeftButtonDown);
lstContextMenu.Items.Add(txb);
}
//把生成的选项集合添加到Grid里
Grid rootGrid = new Grid()
{
HorizontalAlignment = System.Windows.HorizontalAlignment.Left,
VerticalAlignment = System.Windows.VerticalAlignment.Top,
Margin = new Thickness(currentMousePosition.X, currentMousePosition.Y, 0, 0)
};
rootGrid.Children.Add(lstContextMenu);
return rootGrid;
}
void txb_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
txbMessage.Text = "您选择的是:" + (sender as TextBlock).Text;
HidePopup();
}
private void HidePopup()
{
popup.IsOpen = false;
}
void brdRightClickZone_MouseRightButtonDown(object sender, MouseButtonEventArgs e)
{
//如果这里不进行Hanled,那么silverlight自己的Framwork就会把它Handled;
//Silverlight本身自己的右键菜单就会显示出来。所以这里必须要Handled
//这里的Hanled的意思是当前对象要处理这个事件。
//RoutedEventArgs.Handled 属性 :获取或设置一个值,该值指示路由事件在路由过程中的事件处理当前状态。
//如果进行设置,请在要将事件标记为已处理时设置为 true;否则设置为 false。
//如果读取此值,true 指示某个类处理程序或路由过程中的某一实例处理程序已经将此事件标记为已处理。false 指示没有任何此类处理程序将事件标记为已处理。
e.Handled = true;
}
}
}