Виды анимаций для WPF

75

В прикладном интерфейсе Windows Presentation Foundation API поддерживается ряд полезных способов анимации, которые, к сожалению, не находят поддержки в текущей версии платформы Silverlight. В первом из этих способов применяются траектории движения, с помощью которых можно легко перемещать элементы пользовательского интерфейса по объекту типа Path, нарисованному инструментом Pen или Pencil. И хотя аналогичного результата можно, конечно, добиться и в приложении Silverlight, для этого потребуется значительно больше усилий.

Второй характерный для платформы WPF способ анимации состоит в применении триггеров для взаимодействия с раскадровкой. На платформе WPF триггер обозначает применявшийся некогда способ реагирования на условие наступление события в разметке XAML.

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

Вам, возможно, известно, что среда триггеров на платформе WPF первоначально предназначалась для того, чтобы разработчики могли внедрять визуальные подсказки в специальные шаблоны с целью переопределить пользовательский интерфейс в отношении элементов управления и форм.

Несмотря на весьма ограниченную поддержку триггеров на платформе Silverlight, по тому же самому принципу действует диспетчер визуальных состояний (VSM). В действительности диспетчер VSM был настолько хорошо принят в программистских кругах, что на платформе WPF был внедрен свой вариант VSM в ее прикладной интерфейс API, начиная с версии .NET 4.0. С учетом этого обстоятельства у разработчиков приложений на платформе WPF теперь имеются два варианта выбора, когда дело доходит до внедрения визуальных подсказок в специальные шаблоны: триггеры или диспетчер VSM.

Работа с траекториями движения на платформе WPF

В Expression Blend предоставляется очень удобная возможность автоматически формировать на платформе WPF раскадровку, в которой выбранный объект должен перемещаться по предварительно заданной траектории движения. В частности, траектории движения можно использовать для перемещения специальных графических элементов по вершинам линейного графика, показывая прибыли компании, что, конечно, приятнее чем убытки, а возможно и для перемещения элемента управления Image.

Траектория движения создается в среде Expression Blend довольно просто. В качестве примера создайте новый проект приложения WPF. Как и при построении специального объекта раскадровки, ваша первая задача в данном случае - определить те объекты, которые должны перемещаться по данной траектории движения. А поскольку для этой цели может быть использован любой объект создайте несколько разных элементов пользовательского интерфейса по своему усмотрению, например Ellipse, Button и Rectangle. Затем присвойте каждому из этих объектов подходящее имя в поле Name на панели Properties.

После определения ряда объектов в качестве целевых для анимации по траектории ваша следующая задача — создать траектории движения. Для этой цели можете выбрать соответствующие элементы управления из категории Shapes в библиотеке ресурсов или нарисовать контуры траекторий произвольной геометрической формы инструментами Pen и Pencil.

Итак, создайте три разные геометрические формы на монтажном столе (их местоположение, размеры и конфигурация особого значения не имеют). Но ради поддержания порядка на монтажном столе присвойте каждой созданной форме будущей траектории движения подходящее имя, например myStar, myPolygon и myArc.

Кроме того для каждой геометрической формы будущей траектории движения (в данном случае звезды, многоугольника и дуги) рекомендуется настроить свойство Fill на режим раскраски No brush в редакторе кистей, а также установить значение в пределах 2-3 в свойстве StrokeThickness, доступном в области Appearance на панели Properties чтобы траектории движения было лучше видно. Ниже приведен пример:

Контуры, определяющие анимацию по траектории

Выберите на панели Objects and Timeline контур первой формы, чтобы преобразовать его в траекторию движения (в данном случае это контур в форме звезды). Щелкните правой кнопкой мыши на узле этого объекта в иерархическом представлении и выберите команду Path --> Convert to Motion Path (Контур --> Преобразовать в траекторию движения) из всплывающего контекстного меню:

Преобразование контура в траекторию движения

После выбора этой команды появится диалоговое окно, в котором можете далее выбрать один или несколько объектов для перемещения по траектории движения, преобразуемой из контура заданной формы. В данном случае выберите круг в качестве одного из целевых объектов:

Выбор объекта для перемещения по траектории

Как только вы выберете целевой объект, будет создан новый объект раскадровки Storyboard1 (он появится в верхней части иерархического представления на панели Objects and Timeline). Переименуйте этот объект описанным ранее способом в MoveShapes. Обратите внимание на то, что после создания раскадровки вы сможете воспользоваться любым из рассмотренных ранее способов для настройки свойств этой раскадровки (режима автоматического изменения на обратное направление, направление воспроизведения анимации, продолжительности анимации и т.д.). Кроме того можете изменить начальный и конечный моменты каждого промежутка времени между ключевыми кадрами.

Настройте анимационную последовательность таким образом, чтобы она начиналась на нульсекундной отметке и оканчивалась на пятисекундной. Таким образом, вращательное движение круга по траектории в форме звезды будет продолжаться около 5 секунд.

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

В качестве примера на рисунке показано, что общая продолжительность всей анимации составляет восемь секунд, хотя движение каждого целевого объекта (круга, кнопки и прямоугольника) начинается и оканчивается в разные моменты времени:

Анимация движения каждого целевого объекта

Для того чтобы сделать рассматриваемый здесь пример более интересным, организуйте на панели Properties обработку события Click, связанного с объектом типа Button. Так, если щелкнуть на этом объекте, появится информативное окно сообщения You clicked me!, как показано в приведенном ниже коде обработчика событий:

private void buttonOne_Click(object sender, System.Windows.RoutedEventArgs e)
		{
			MessageBox.Show("You clicked me!");
		}

Запустите приложение на выполнение, нажав функциональную клавишу <F5> или <Ctrl+F5>, в итоге все три объекта последуют по заданным траекториям объектов. (Проверьте свою реакцию, успеете ли вы щелкнуть на кнопке, пока она движется.) В отличие от рассмотренного ранее примера проекта на платформе Silverlight, в данном случае анимация начинается, как только главное окно приложения (объект типа Window) загрузится в оперативную память. Такое поведение объясняется тем, что по умолчанию анимация начинается после загрузки главного окна благодаря приведенной ниже разметке XAML:

<Window.Triggers>
		<EventTrigger RoutedEvent="FrameworkElement.Loaded">
			<BeginStoryboard x:Name="MoveStar_BeginStoryboard" Storyboard="{StaticResource MoveStar}"/>
			<BeginStoryboard Storyboard="{StaticResource OpacityRect}"/>
		</EventTrigger>
	</Window.Triggers>

Найдите эту разметку, используя редактор XAML, доступный на монтажном столе. Как видите в этой разметке описывается применяемый на платформе WPF триггер с помощью которого, как известно, перехватывается условие наступления события, что избавляет от необходимости писать для этой цели специальный код на C# или VB. В данном случае триггер проверяет момент наступления события Loaded, связанного с загрузкой объекта типа Window в оперативную память. Когда это событие наступает, обрабатывается элемент разметки <BeginStoryboard> и начинается воспроизведение анимации по раскадровке, представленной объектом MoveShapes.

Несмотря на то что данный триггер анимации на платформе WPF оказывается очень удобным в тех случаях, когда требуется быстро проверить, каким образом анимация будет вести себя во время выполнения разрабатываемого приложения, следует ясно отдавать себе отчет в том, что не всякая анимация должна начинаться после загрузки основного окна приложения. Вполне возможно, что вам потребуется начинать анимацию только в том случае, если пользователь выберет конкретный пункт меню, щелкнет на отдельной кнопке или выполнит иное предусмотренное действие.

Разумеется, события можно обрабатывать и вручную, начиная анимацию по раскадровке непосредственно в коде? а среда триггеров на платформе WPF предоставляет лишь альтернативный вариант запуска анимации без написания специального кода.

Пройди тесты
Лучший чат для C# программистов