WPF路由事件,订阅自定义事件

5

我正在尝试让手动触发的子控件路由事件能够冒泡并在主网格级别进行处理。我想要做的基本上像这样:

<Grid Name="Root" WpfApplication5:SpecialEvent.Tap="Catcher_Tap">
    <Grid.RowDefinitions>
        <RowDefinition Height="40" />
        <RowDefinition Height="40" />
        <RowDefinition Height="*" />
    </Grid.RowDefinitions>
    <WpfApplication5:UserControl2 Grid.Row="0" x:Name="Catcher" />
    <WpfApplication5:UserControl1 Grid.Row="1" />
    <Frame Grid.Row="2" Source="Page1.xaml" />
</Grid>

但是当我运行我的示例时,演示框架中出现了空引用,应用程序从未初始化,在尝试加载/初始化XAML(InitializeComponent())时失败。这是包含事件的小文件:

public class SpecialEvent
{
    public static readonly RoutedEvent TapEvent = EventManager.RegisterRoutedEvent(
        "Tap", RoutingStrategy.Direct, typeof(RoutedEventHandler), typeof(UserControl1));

    // Provide CLR accessors for the event
    public event RoutedEventHandler Tap;
}

我基本上想要复制ButtonBase.Click的行为,使得父级可以订阅其子元素的任何按钮点击方法。但是,这似乎只适用于ButtonBase.Click()。也就是说,当我将自定义的WpfApplication5:SpecialEvent.Tap="Catcher_Tap"替换为ButtonBase.Click="Catcher_Tap"时,它才能正常工作。你有什么建议吗?ButtonBase在做些什么而我又未做到呢?

2个回答

8

在进一步尝试后,我发现可以通过主窗口的代码后端来实现我所需的功能,代码如下:

public MainWindow()
    {
        InitializeComponent();
        Root.AddHandler(SpecialEvent.TapEvent, new RoutedEventHandler(Catcher_Tap));
    }

由于某些原因,在XAML中像ButtonBase()那样指定它 不起作用,但在代码后台添加Handler则可以。


3
您提供的代码确实注册了一个自定义事件,但它没有注册一个附加的自定义事件。如果您想要使用附加的语法来使用您的事件,您将不得不显式地实现Add*HandlerRemove*Handler方法。请参见此 MSDN 文章中的“将您自己定义的附加事件定义为路由事件”一节。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接