简体   繁体   English

背后的代码中的System.Windows.Interactivity.EventTrigger在某些控件上有效,但在其他控件上则无效

[英]System.Windows.Interactivity.EventTrigger in codebehind works on some Controls, but not others

I have an application where I'm adding controls during runtime and want to attach EventTrigger(s) that are PlaySoundAction . 我有一个应用程序,我在运行时在其中添加控件,并希望附加PlaySoundAction的 EventTrigger In XAML this is easy, but with the need to generate controls on the fly and add these Triggers it becomes a bit more difficult. 在XAML中,这很容易,但是由于需要动态生成控件并添加这些触发器,因此变得更加困难。

I asked in a previous question and was able to get part way there and with recent testing I have come to a conclusion on what I can do to solve it, but was hoping there might be something I'm missing. 我在上一个问题中 ,能够做到这一点,并且通过最近的测试,我得出了解决该问题的方法的结论,但我希望可能会缺少一些东西。 I am able to get the EventTrigger working on a Button control, but not on a RegularPolygon and I'm unable to take an easy route on embedding a button inside of the RegularPolygon to achieve the results I want because it is not a ContentControl. 我能够使EventTrigger在Button控件上工作,但不能在RegularPolygon上工作,并且我无法轻松地将按钮嵌入RegularPolygon内以实现所需的结果,因为它不是ContentControl。

This is what I currently have this method for adding new RegularPolygons to a container (Canvas): 这是我目前使用此方法向容器(画布)添加新的RegularPolygons的方法:

public RegularPolygon AddShape(Panel container)
{
    RegularPolygon shape = new RegularPolygon();

    // ShapeColors is a List<SolidColorBrush> that has been prepopulated
    // _random is a Random() from .NET
    shape.Fill = ShapeColors[_random.Next(0, ColorCount - 1)];
    shape.Stretch = Stretch.Fill;
    shape.PointCount = _random.Next(3, 6);
    shape.UseLayoutRounding = false;
    shape.Stroke = new SolidColorBrush(Colors.Black);
    shape.Width = _random.Next(50, 150);
    shape.Height = _random.Next(50, 150);
    // UI_Tap is an arbitrary function for handling the Tap event
    shape.Tap += UI_Tap;

    System.Windows.Interactivity.EventTrigger trigger = new System.Windows.Interactivity.EventTrigger("Tap");
    PlaySoundAction correct = new PlaySoundAction();
    correct.Source = new Uri("/Sounds/Correct.mp3", UriKind.RelativeOrAbsolute);
    correct.Volume = 1;

    trigger.Actions.Add(correct);

    //Button b = new Button();
    //b.Content = "This is button B";
    //System.Windows.Interactivity.Interaction.GetTriggers(b).Add(trigger);
    //container.Children.Add(b);

    // Comment this line out when uncommenting Button b block because Triggers 
    // can only be associated with one element
    System.Windows.Interactivity.Interaction.GetTriggers(shape).Add(trigger);

    Canvas.SetLeft(shape, _random.Next((int)(shape.Width / 2), (int)(container.Width - (shape.Width / 2))));
    Canvas.SetTop(shape, _random.Next((int)(shape.Height / 2), (int)(container.Height - (shape.Height / 2))));
    container.Children.Add(shape);

    return shape;
}

I can see all my RegularPolygons appear on the screen. 我可以看到我所有的RegularPolygons出现在屏幕上。 I have tested to make sure the path to the sound file works by having other test controls attempt to reference it at the listed location. 我已经过测试,通过让其他测试控件尝试在列出的位置引用声音文件,来确保声音文件的路径有效。 No luck getting the EventTrigger with the PlaySoundAction to work. 让EventTrigger和PlaySoundAction一起工作是没有运气的。 If I uncomment the lines around button b I can see the button added and Tap it to hear the sound play. 如果取消注释按钮b周围的线条,则可以看到已添加的按钮,然后点按它以收听声音。

I can get a RegularPolygon to work with a PlaySoundAction EventTrigger in XAML as follows: 我可以使RegularPolygon与XAML中的PlaySoundAction EventTrigger一起使用,如下所示:

<es:RegularPolygon x:Name="haxx" Fill="#FFF4F4F5" Height="100" InnerRadius="1" Canvas.Left="125" PointCount="5" Stretch="Fill" Stroke="Black" Canvas.Top="187" UseLayoutRounding="False" Width="100">
    <i:Interaction.Triggers>
        <i:EventTrigger EventName="Tap">
            <eim:PlaySoundAction Source="/Sounds/Correct.mp3"/>
        </i:EventTrigger>
    </i:Interaction.Triggers>
</es:RegularPolygon>

My upcoming solution would be to create a custom control that will let me use the shape of the RegularPolygon with the functionality of the Button as I can get this to work from codebehind. 我即将到来的解决方案是创建一个自定义控件,该控件使我可以将RegularPolygon的形状与Button的功能一起使用,因为我可以从代码隐藏中使它起作用。 Is there anything that I'm missing that is preventing me from having this EventTrigger work? 我有什么想让我无法使用EventTrigger的东西吗?

This was a case of not enough information in the question asked. 这是在所问问题中信息不足的情况。 The UI_Tap(...) method had a few goals: UI_Tap(...)方法有一些目标:

  • Play the sound when the RegularPolygon is tapped 轻按RegularPolygon时播放声音
  • Determine if more objects need to drawn to the screen (to avoid running out of things to touch) 确定是否需要在屏幕上绘制更多对象(以避免耗尽触摸的物体)
  • Remove the Tap'd RegularPolygon from the parent container 从父容器中删除Tap'd RegularPolygon

What got was removing the object from the parent container and it did not immediately hit me that my object was going to be prevented from executing an EventTrigger associated with it. 得到的是从父容器中删除该对象,但并没有立即使我感到无法阻止我的对象执行与其关联的EventTrigger。 This is also why hardcoding in a RegularPolygon onto the MainPage.xaml worked as well as the Button above due to the fact that I never attempted to remove them inside of the Tap event handler. 这也是为什么在RegularPolygon中将硬编码到MainPage.xaml上与上面的Button一样好的原因,因为我从未尝试在Tap事件处理程序中删除它们。

I had some suggestions of tying the EventTrigger for the PlaySoundAction to the ManipulationStartedEvent because it occurs prior to the Tap event and this would work, but I'm going a more complex route of using XNA libraries to play a SoundEffect during an update loop. 我有一些将PlaySoundAction的EventTrigger绑定到ManipulationStartedEvent的建议,因为它发生在Tap事件之前,并且可以工作,但是我要走一条更复杂的路线,即使用XNA库在更新循环中播放SoundEffect。 It involves creating an IApplicationLifetimeService and queuing sounds to play in FrameDispatchTimer_Tick event like this: 它涉及创建一个IApplicationLifetimeService并排队声音以在FrameDispatchTimer_Tick事件中播放,如下所示:

FrameworkDispatcher.Update has not been called and what to do about it 未调用FrameworkDispatcher.Update及其处理方法

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM