WP7 VisualState изменить программно - PullRequest
1 голос
/ 09 июня 2011

Я пытаюсь создать изображение, чтобы при его нажатии появлялось небольшое всплывающее окно. При повторном прикосновении к нему (или в любом другом месте) оно должно исчезнуть.
Я создал всплывающее окно и несколько визуальных переходов состояний, чтобы скрыть и свернуть

<Grid x:Name="LayoutRoot" Background="Transparent">
    <VisualStateManager.VisualStateGroups>
                <VisualStateGroup x:Name="PopupVisibility">
                    <VisualState x:Name="PopupVisible">
                        <Storyboard>
                            <ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="PopupControl">
                                <DiscreteObjectKeyFrame KeyTime="0">
                                    <DiscreteObjectKeyFrame.Value>
                                        <Visibility>Visible</Visibility>
                                    </DiscreteObjectKeyFrame.Value>
                                </DiscreteObjectKeyFrame>
                            </ObjectAnimationUsingKeyFrames>
                            <DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="PopupControl">
                                <EasingDoubleKeyFrame KeyTime="0" Value="0"/>
                                <EasingDoubleKeyFrame KeyTime="0:0:0.5" Value="1"/>
                            </DoubleAnimationUsingKeyFrames>
                            <DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.ScaleX)" Storyboard.TargetName="PopupControl">
                                <EasingDoubleKeyFrame KeyTime="0" Value="0"/>
                                <EasingDoubleKeyFrame KeyTime="0:0:0.5" Value="1"/>
                            </DoubleAnimationUsingKeyFrames>
                            <DoubleAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.ScaleY)" Storyboard.TargetName="PopupControl">
                                <EasingDoubleKeyFrame KeyTime="0" Value="0"/>
                                <EasingDoubleKeyFrame KeyTime="0:0:0.5" Value="1"/>
                            </DoubleAnimationUsingKeyFrames>
                        </Storyboard>
                    </VisualState>
                    <VisualState x:Name="PopupCollapsed">
                        <Storyboard>
                            <DoubleAnimation Duration="0:0:0.5" To="0" Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.ScaleX)" Storyboard.TargetName="PopupControl" d:IsOptimized="True"/>
                            <DoubleAnimation Duration="0:0:0.5" To="0" Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.ScaleY)" Storyboard.TargetName="PopupControl" d:IsOptimized="True"/>
                            <DoubleAnimation Duration="0:0:0.5" To="0" Storyboard.TargetProperty="(UIElement.Opacity)" Storyboard.TargetName="PopupControl" d:IsOptimized="True"/>
                            <ObjectAnimationUsingKeyFrames Storyboard.TargetProperty="(UIElement.Visibility)" Storyboard.TargetName="PopupControl">
                                <DiscreteObjectKeyFrame KeyTime="0:0:0.5">
                                    <DiscreteObjectKeyFrame.Value>
                                        <Visibility>Visible</Visibility>
                                    </DiscreteObjectKeyFrame.Value>
                                </DiscreteObjectKeyFrame>
                                <DiscreteObjectKeyFrame KeyTime="0:0:0.7">
                                    <DiscreteObjectKeyFrame.Value>
                                        <Visibility>Collapsed</Visibility>
                                    </DiscreteObjectKeyFrame.Value>
                                </DiscreteObjectKeyFrame>
                            </ObjectAnimationUsingKeyFrames>
                        </Storyboard>
                    </VisualState>
                </VisualStateGroup>
            </VisualStateManager.VisualStateGroups>

<Button Content="Text" HorizontalAlignment="Right" Margin="0,0,12,-37" Width="152" Background="#00C06B6B" Height="75" VerticalAlignment="Bottom" Visibility="Visible">
            <Custom:Interaction.Triggers>
                <Custom:EventTrigger EventName="Click">
                    <ic:GoToStateAction x:Name="GoToStatePopupVisible" StateName="PopupVisible"/>
                </Custom:EventTrigger>
                <Custom:EventTrigger EventName="LostFocus">
                    <ic:GoToStateAction x:Name="LostFocus" StateName="PopupCollapsed"/>
                </Custom:EventTrigger>
            </Custom:Interaction.Triggers>
        </Button>

 <Grid x:Name="PopupControl" Height="241" Margin="39,-28,203,0" Grid.Row="1" VerticalAlignment="Top" RenderTransformOrigin="0.5,0.5">





                <Grid.RenderTransform>
                <CompositeTransform/>
            </Grid.RenderTransform>
            <Rectangle Stroke="Black">
                <Rectangle.Fill>
                    <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
                        <GradientStop Color="#FF726969" Offset="1"/>
                        <GradientStop Color="White"/>
                    </LinearGradientBrush>
                </Rectangle.Fill>
            </Rectangle>
            <TextBlock TextWrapping="Wrap" Text="TextBlock" d:LayoutOverrides="Width" Foreground="#FF1D0E0E" Margin="5"/>
        </Grid>
<Image HorizontalAlignment="Right" Height="100" Margin="0,-38,37,0" Grid.Row="1" VerticalAlignment="Top" Width="100" Source="Images/pushpin.jpg" ManipulationStarted="Image_ManipulationStarted">
        </Image>

</Grid>

Я попытался использовать Blend, чтобы проверить это, и отлично работает, например, добавив кнопку и создав триггер:

<Button Content="Text" HorizontalAlignment="Right" Margin="0,0,12,-37" Width="152" Background="#00C06B6B" Height="75" VerticalAlignment="Bottom" Visibility="Visible">
            <Custom:Interaction.Triggers>
                <Custom:EventTrigger EventName="Click">
                    <ic:GoToStateAction x:Name="GoToStatePopupVisible" StateName="PopupVisible"/>
                </Custom:EventTrigger>
                <Custom:EventTrigger EventName="LostFocus">
                    <ic:GoToStateAction x:Name="LostFocus" StateName="PopupCollapsed"/>
                </Custom:EventTrigger>
            </Custom:Interaction.Triggers>
        </Button>

Однако, когда я пробую «настоящую» вещь, мне нужно больше логики, чем эта. Если я нажимаю на изображение, и оно видно, я хочу, чтобы оно перешло в свернутый и наоборот. Поэтому я сохраняю свое текущее состояние видимости

(VisualStateManager.GetVisualStateGroups(LayoutRoot)[0] as VisualStateGroup).CurrentStateChanged += new EventHandler<VisualStateChangedEventArgs>(MainPage_CurrentStateChanged);

public string CurrentState { get; set; }

        void MainPage_CurrentStateChanged(object sender, VisualStateChangedEventArgs e)
        {
            CurrentState = e.NewState.Name;
        }

А потом я создаю изображение:

<Image HorizontalAlignment="Right" Height="100" Margin="0,-38,37,0" Grid.Row="1" VerticalAlignment="Top" Width="100" Source="Images/pushpin.jpg" ManipulationStarted="Image_ManipulationStarted">
            </Image>

Наконец, я программно пытаюсь сделать то же самое, что и Eventtrigger, но с некоторой логикой:

private void Image_ManipulationStarted(object sender, ManipulationStartedEventArgs e)
        {
            switch (CurrentState)
            {
                case "PopupVisible":
                    {
                        ExtendedVisualStateManager.GoToElementState(LayoutRoot, "PopupCollapsed", true);
                        break;
                    }
                case "PopupCollapsed":
                    {
                        ExtendedVisualStateManager.GoToElementState(LayoutRoot, "PopupVisible", true);
                        break;
                    }
            }
        }

Я пробовал оба метода VisualStateManager и ExtendedVisualStateManager GoToState и GoToElementState, но безрезультатно. Методы всегда возвращают false, и на экране ничего не меняется. Что я делаю не так?

1 Ответ

1 голос
/ 09 июня 2011

Я предполагаю, что вы отладили код, чтобы вы знали, что элемент управления попадает в обработчик ManipulationSTarted.

Прим.в msdn VisualStateManager.GoToState документация: " Если stateName не существует в ControlTemplate элемента управления, GoToState не предпринимает никаких действий и возвращает false. "

Из приведенного выше кода я не могусудите, что такое LayoutRoot и действительно ли состояния определены в этом элементе.(Дополнительное замечание: Popup выполняет некоторые манипуляции с визуальным деревом, что в некоторых случаях может объяснить поведение, описанное выше.)

С другой стороны, я не понимаю, почему вы используете Xaml в этом случае.На мой взгляд, вы можете сделать это намного проще в коде.(Не говоря о производительности.):

  1. Создайте 2 раскадровки в коде

  2. Запустите их по мере необходимости из обработчика ManipulationStarted.

Если вы не знаете, как работать с раскадровками в коде, посмотрите, например, эту мою статью .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...