2

I'm wondering if I can have a individual component in a control have an event. For example, I've created my own control, and with VisualStateManager I'm able to handle several events that fire for the control as a whole, I'd like just my togglebutton in the controlto fire the mouseover event. Currently any area of the control that the mouse is over fires the mouseover which ruins the coloranimation effect i'm trying to get, I want the coloranimation to only happen when the toggle button has a mouse over, my control has a contentpresent allowing for other content, i don't want that piece to fire the event.

Example of what i'm talking about below in generic.xaml file.

<Style TargetType="local:MyControl">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="local:MyControl">
                <Grid>
                    <VisualStateManager.VisualStateGroups>
                        <VisualStateGroup x:Name="ViewStates">

                            <VisualState x:Name="Expanded">
                                <Storyboard>
                                    <DoubleAnimation Storyboard.TargetName="ContentScaleTransform" Storyboard.TargetProperty="ScaleY" To="1" Duration="0"/>
                                </Storyboard>
                            </VisualState>
                            <VisualState x:Name="Collapsed">
                                <Storyboard>
                                    <DoubleAnimation Storyboard.TargetName="ContentScaleTransform" Storyboard.TargetProperty="ScaleY" To="0" Duration="0"/>
                                </Storyboard>
                            </VisualState>
                            <VisualState x:Name="MouseOver">
                                <Storyboard>
                                    <!-- This fires for any part of the control, is it possible to just create a mouseover for the ToggleButton below? -->
                                </Storyboard>
                            </VisualState>
                        </VisualStateGroup>
                    </VisualStateManager.VisualStateGroups>
                    <Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" CornerRadius="{TemplateBinding CornerRadius}" Background="{TemplateBinding Background}">
                        <Grid>
                            <Grid.RowDefinitions>
                                <RowDefinition Height="Auto"/>
                                <RowDefinition Height="Auto"/>
                            </Grid.RowDefinitions>
                            <Grid Margin="3">
                                <Grid.ColumnDefinitions>
                                    <ColumnDefinition Width="*"/>
                                </Grid.ColumnDefinitions>
                                <ToggleButton Grid.Column="0" Content="{TemplateBinding HeaderContent}" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"  RenderTransformOrigin="0.5,0.5" Margin="1" x:Name="ExpandCollapseButton">

                                </ToggleButton>
                            </Grid>
                            <ContentPresenter Grid.Row="1" Margin="5" Content="{TemplateBinding Content}" x:Name="Content">
                                <ContentPresenter.RenderTransform>
                                    <ScaleTransform x:Name="ContentScaleTransform"/>
                                </ContentPresenter.RenderTransform>
                            </ContentPresenter>
                        </Grid>
                    </Border>

                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>
4

2 回答 2

2

Bob,您可以像这样从您的班级访问切换按钮:

ToggleButton myToggleButton = GetTemplateChild("toggleButton") as ToggleButton;

在课堂上创建您想要的活动。您可能需要覆盖 OnApplyTemplate 方法并在那里创建您的事件,我仍在研究这部分并且还没有完全理解它,您将不得不使用它。我确实覆盖了我的 OnApplyTemplate 并且它对我有用。

ToggleButton myToggleButton;
public override void OnApplyTemplate() {
    base.OnApplyTemplate();
    myToggleButton = GetTemplateChild("toggleButton") as ToggleButton;
    myToggleButton.MouseEnter += new MouseEventHandler(myToggleButton_MouseEnter);
}
void myToggleButton_MouseEnter(object sender, MouseEventArgs e) {
        VisualStateManager.GoToState(this, "MouseEnter", true);
    }

还要确保在顶部设置您的模板:

[TemplateVisualState(Name = "MouseEnter", GroupName = "ViewStates")]

VisualState 可以存在于您设置其他视觉状态的 generic.xaml 文件中,并且不需要位于内部 ToggleButton 中。

<VisualState x:Name="MouseEnter">
    <Storyboard>
        <ColorAnimation Storyboard.TargetName="toggleButton" Storyboard.TargetProperty="(ToggleButton.SomeProperty).(SolidColorBrush.Color)" To="SomeColor"/>
    </Storyboard>
</VisualState>
于 2011-08-04T19:29:06.587 回答
1

首先,让我们的术语正确,您不是在谈论“事件”,而是在谈论“视觉状态”。“MouseOver”是一种视觉状态。它由控件内的代码负责决定控件处于哪种视觉状态。

通常,控件中的代码将使用 MouseEnter 和 MouseLeave 事件来设置一个布尔值以指示鼠标在控件上,然后调用一些UpdateStates方法,开发人员将在其中包含逻辑以确定控​​件当前应该处于哪些视觉状态。

在您的情况下,而不是使用控件MouseEnterMouseLeave事件,而是将这些处理程序附加到您的内部ToggleButton

于 2011-08-03T20:48:51.623 回答