Запуск анимации из ViewModel в WPF/MVVM
Я пишу приложение MVVM и начал вводить несколько анимаций. Я хочу назвать что-то на ViewModel, который запускает раскадровку. этот блог имел многообещающий подход к нему, но на самом деле это не работает. Обработчик IDChanged никогда не срабатывает по какой-либо причине.
Я также обнаружил, что вы можете запускать анимации на EventTriggers, но я не знаю, как поднять один на ViewModel.
4 ответов
Я сделал это с помощью DataTrigger и привязки его к свойству в моей ViewModel. Когда свойство" FlashingBackGround "получает значение" ON", начинается анимация раскадровки.
также обязательно включите в свой проект ссылку на "Microsoft.Выражение.Взаимодействия"
XAML: (это происходит непосредственно в корневом узле)
<Window
xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
x:Name="window" >
...
<i:Interaction.Triggers>
<ei:DataTrigger Binding="{Binding FlashingBackground, Mode=OneWay}" Value="ON">
<ei:ControlStoryboardAction Storyboard="{StaticResource MyAnimation}"
ControlStoryboardOption="Play"/>
</ei:DataTrigger>
</i:Interaction.Triggers>
...
</Window>
ViewModel:
private void TurnOnFlashingBackround()
{
FlashingBackground = "ON";
}
private string _FlashingBackround = "OFF";
public string FlashingBackground
{
get { return _FlashingBackround; }
private set
{
if (FlashingBackground == value)
{
return;
}
_FlashingBackround = value;
this.OnPropertyChanged("FlashingBackground");
}
}
public new event PropertyChangedEventHandler PropertyChanged;
private void OnPropertyChanged(string propertyName)
{
if (this.PropertyChanged != null)
{
this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
наконец, Viewmodel должен наследовать от "INotifyPropertyChanged"
У меня есть свойство в моей виртуальной машине, которое отражает состояние приложения. Анимированные элементы представления имеют триггер данных, который запускает раскадровку, когда свойство VM имеет определенное значение.
Я закончил тем, что добавил событие AnimationStarted в мою ViewModel с ключевой строкой для какой анимации это. Затем в представлении я создаю анимацию программно, подписываюсь на событие AnimationStarted и отключаю соответствующую анимацию при ее запуске.
я столкнулся с той же проблемой, и ни один из этих сообщений не помог, потому что анимации находятся в коде, а некоторые из них были большими и сложными и требовали изменяющихся переменных, поэтому они должны были оставаться в коде. Я разрешил его, добавив свойства зависимостей в пользовательский элемент управления (представление), которые запускают анимации, и привязав их к свойствам в модели представления. Не знаю (/care), если это нарушает что-то или другое, потому что это работает очень хорошо! овации, stepp
выдержка:
(просмотр) код Usercontrol позади:
public override void OnApplyTemplate()
{
base.OnApplyTemplate();
SetAnimationBindings();
}
private void SetAnimationBindings()
{
_dialogStartPosition = mbFolderBrowse.Margin;
var propName = "StartDialogAnimation";
var binding = new Binding(propName) { Mode = BindingMode.TwoWay };
this.SetBinding(DialogAnimationProperty, binding);
propName = "StartProgressAnimation";
binding = new Binding(propName) { Mode = BindingMode.TwoWay };
this.SetBinding(ProgressAnimationProperty, binding);
}
#region Animation Properties
#region DialogAnimation
public static readonly DependencyProperty DialogAnimationProperty =
DependencyProperty.Register("DialogAnimation", typeof(bool),
typeof(Manage), new FrameworkPropertyMetadata(false, FrameworkPropertyMetadataOptions.BindsTwoWayByDefault, OnDialogAnimationChanged));
public bool DialogAnimation
{
get { return (bool)this.GetValue(DialogAnimationProperty); }
set
{
var oldValue = (bool)this.GetValue(DialogAnimationProperty);
if (oldValue != value) this.SetValue(DialogAnimationProperty, value);
}
}
private static void OnDialogAnimationChanged(DependencyObject o, DependencyPropertyChangedEventArgs e)
{
Manage m = o as Manage;
if ((bool)e.NewValue == true)
m.SlideInDialogPanel(); // animations
else
m.SlideOutDialogPanel();
}
#endregion
Вид-Модель:
public bool StartDialogAnimation
{
get { return _startDialogAnimation; }
set
{
if (_startDialogAnimation != value)
{
_startDialogAnimation = value;
RaisePropertyChanged("StartDialogAnimation");
}
}
}