WPF에서 트리거란 이벤트가 발생했을 때 변화를 시키는 것을 의미합니다. 일반적으로 Style의 보조로 많이 사용합니다.
먼저 트리거 사용법을 알아보겠습니다.
1. 일반 트리거
style태그 아래에 아래 형식으로 코드를 작성하시면 됩니다.
<Style.Triggers>
<Trigger Property="Control.이벤트" Value="True">
<Setter Property="Control.속성" Value="값">
</Setter>
</Trigger>
</Style.Triggers>
예제로 마우스로 클릭하고 있는 상태일 때 글자색이 빨간색으로 변하는 코드를 만들어보겠습니다.
<Window.Resources>
<Style x:Key="testStyle">
<Setter Property="Button.Background">
<Setter.Value>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="Black"/>
<GradientStop Color="#FF16CEA8" Offset="1"/>
<GradientStop Color="#FF0C735E" Offset="0.563"/>
<GradientStop Color="#FF0B6C58" Offset="0.533"/>
</LinearGradientBrush>
</Setter.Value>
</Setter>
<Style.Triggers>
<!--컨트롤의 IsMouseCaptured 속성이 true일때 트리거 동작-->
<Trigger Property="Control.IsMouseCaptured" Value="True">
<Setter Property="Control.Foreground" Value="Red">
</Setter>
</Trigger>
</Style.Triggers>
</Style>
</Window.Resources>
실행결과
글자색이 변하는 것을 확인할 수 있습니다.
2. 데이터트리거
데이터 트리거의 사용법은 아래와 같습니다.
<Style.Triggers>
<DataTrigger Binding="{Binding ElementName=컨트롤의 x:name,Path=이벤트}" Value="값">
<Setter Property="Control.속성" Value="값"></Setter>
<Setter Property="Control.속성" Value="값"></Setter>
</DataTrigger>
</Style.Triggers>
<setter>는 여러개를 걸 수도 있습니다.
예제를 보겠습니다.
체크박스 클릭시 style이 있는 컨트롤이 보이지 않도록 하겠습니다.
<Window.Resources>
<Style x:Key="testStyle">
<Setter Property="Button.Background">
<Setter.Value>
<LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
<GradientStop Color="Black"/>
<GradientStop Color="#FF16CEA8" Offset="1"/>
<GradientStop Color="#FF0C735E" Offset="0.563"/>
<GradientStop Color="#FF0B6C58" Offset="0.533"/>
</LinearGradientBrush>
</Setter.Value>
</Setter>
<Style.Triggers>
<DataTrigger Binding="{Binding ElementName=check1,Path=IsChecked}" Value="True">
<Setter Property="Control.Foreground" Value="Purple"></Setter>
<Setter Property="Control.Visibility" Value="Hidden"></Setter>
</DataTrigger>
</Style.Triggers>
</Style>
</Window.Resources>
실행결과
체크되지 않았을 때
체크되었을 때
예제2)
클래스를 생성하고 객체를 생성하여 객체의 속성이 변겨오디면 해당 속성값대로 프로그래스바가 움직이도록 만들어보겠습니다.
먼저 프로젝트를 우클릭하여 새항목을 클릭한 후 ViewModels라는 폴더를 만듭니다.
그리고 ViewModels 폴더안에 MainViewModel이라는 클래스를 만듭니다.
그리고 아래와 같은 코드를 추가합니다.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading.Tasks;
namespace WpfApp2.ViewModels
{
//INotifyPropertyChanged는 바인딩이 업데이트되도록 뷰(화면)에게 알려줍니다.
internal class MainViewModel : INotifyPropertyChanged
{
private int progressValue;
public int ProgressValue
{
get { return progressValue; }
set { progressValue = value; }
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
}
그리고 MainWindow.xaml에서 프로그래스바 컨트롤을 추가합니다.
value에는 바인딩 설정을 합니다.
Binding값으로는 public 인 ProgressValue를 넣어야 인식합니다.
<ProgressBar x:Name="progressBar1" Width="200" Height="20" Value="{Binding ProgressValue}"></ProgressBar>
기본값으로 30퍼센트가 채워져있도록 해보겠습니다.
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using WpfApp2.ViewModels;
namespace WpfApp2
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
MainViewModel viewModel;
public MainWindow()
{
InitializeComponent();
viewModel = new MainViewModel();
//MainWindow의 바인딩 경로의 시작점이 됨
viewModel.ProgressValue = 30;
DataContext = viewModel;
}
}
}
실행결과
버튼 클릭시 100%로 채워지도록 해보겠습니다.
MainWindow.cs
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using WpfApp2.ViewModels;
namespace WpfApp2
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
MainViewModel viewModel;
public MainWindow()
{
InitializeComponent();
viewModel = new MainViewModel();
//MainWindow의 바인딩 경로의 시작점이 됨
viewModel.ProgressValue = 30;
DataContext = viewModel;
}
private void Button_Click(object sender, RoutedEventArgs e)
{
//버튼 클릭시 프로그레스바 100으로 변환
viewModel.ProgressValue = 100;
}
}
}
이렇게 코드를 작성하고 실행하면 100으로 변하지 않을 것입니다. 여기서 추가해야될 코드가 있습니다.
MainViewModel.cs에서 set부분을 수정해야 합니다.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading.Tasks;
namespace WpfApp2.ViewModels
{
//INotifyPropertyChanged는 바인딩이 업데이트되도록 뷰(화면)에게 알려줍니다.
internal class MainViewModel : INotifyPropertyChanged
{
private int progressValue;
public int ProgressValue
{
get { return progressValue; }
//수정할 부분
set
{
progressValue = value;
//값이 변경되면 화면도 변경되게 하는 기능
//NotifyPropertyChanged(nameof(변수 또는 객체))
NotifyPropertyChanged(nameof(ProgressValue));
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
}
이렇게 코드를 입력하고 실행하면 버튼 클릭 시 프로그레스바가 100으로 변경됩니다.
이제는 프로그레스바가 100으로 변경될 때 라벨과 버튼이 보이지 않도록 해보겠습니다.
MainWindow.xaml에 아래코드를 추가하겠습니다.
<Style.Triggers>
<!--progressBar1의 value가 100이면 동작-->
<DataTrigger Binding="{Binding ElementName=progressBar1,Path=Value}" Value="100">
<Setter Property="Control.Visibility" Value="Hidden"></Setter>
</DataTrigger>
</Style.Triggers>
실행결과
3. 애니메이션
<Window x:Class="WpfAnimation.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfAnimation"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800">
<StackPanel>
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="1*"/>
<ColumnDefinition Width="1*"/>
</Grid.ColumnDefinitions>
<Grid.Triggers>
<!--그리드 패널이 로드가 되면 애니메이션이 작동-->
<EventTrigger RoutedEvent="Loaded">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Opacity"
From="0" To="1"
Duration="0:0:5"
/>
<!--듀레이션은 시간단위 시간:분:초-->
</Storyboard>
</BeginStoryboard>
</EventTrigger>
<EventTrigger RoutedEvent="MouseEnter">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Width"
From="0" To="350"
Duration="0:0:5"
/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</Grid.Triggers>
<Label FontSize="30">안녕하세요</Label>
<Button Grid.Column="1">버튼</Button>
</Grid>
<Label FontSize="30">안녕하세요2
<Label.Triggers>
<EventTrigger RoutedEvent="MouseEnter">
<BeginStoryboard>
<Storyboard>
<DoubleAnimation Storyboard.TargetProperty="Width"
From="0" To="350"
Duration="0:0:5"
/>
</Storyboard>
</BeginStoryboard>
</EventTrigger>
</Label.Triggers>
</Label>
</StackPanel>
</Window>
코드를 작성하고 실행해보면 애니메이션이 작동하는 것을 확인할 수 있습니다.
trigger는 모든 컨트롤에 있기 때문에 필요한 컨트롤에 이벤트 트리거를 만들어 사용하면 됩니다.
'C# Programming > WPF' 카테고리의 다른 글
[WPF] Settings.settings 만들기 (0) | 2024.05.16 |
---|---|
[WPF] 동기, 비동기 RelayCommand (0) | 2024.05.16 |
[WPF] 스타일(Xaml 리소스) (0) | 2024.05.16 |
[WPF] 모델 생성과 바인딩 (0) | 2024.05.16 |
[WPF] 컨트롤 사용방법 (2) | 2024.05.13 |