[C#/WPF] LinearGradientBrush 클래스 : 애니메이션 이동 길이 구하기
■ LinearGradientBrush 클래스에서 애니메이션 이동 길이를 구하는 방법을 보여준다. ※ GradientStop 컬렉션을 TranslateTransform 클래스 X 속성을 이용해 애니메이션 시키는 경우, 이동시킬 거리를
■ LinearGradientBrush 클래스에서 애니메이션 이동 길이를 구하는 방법을 보여준다. ※ GradientStop 컬렉션을 TranslateTransform 클래스 X 속성을 이용해 애니메이션 시키는 경우, 이동시킬 거리를
■ Timeline 엘리먼트의 RepeatBehavior 속성을 사용하는 방법을 보여준다. ▶ 3번 반복하기 (XAML)
1 2 3 |
RepeatBehavior="3x" |
▶ 1.5번 반복하기 (XAML)
1 2 3 |
RepeatBehavior="1.5x" |
▶ 10초 간격까지만 반복하기
■ Timeline 엘리먼트의 Duration 속성을 사용하는 방법을 보여준다. ▶ 2.5초간 지속하기 (XAML)
1 2 3 |
Duration="0:0:2.5" |
▶ 3분간 지속하기 (XAML)
1 2 3 |
Duration="0:3" |
▶ 7시간 지속하기 (XAML)
■ 베지어 곡선의 Point 리스트를 구하는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 |
using System.Collections.Generic; using System.Windows; #region 베지어 곡선 포인트 리스트 구하기 - GetBezierCurvePointList(startPoint, controlPoint1, controlPoint2, endPoint, pointCount) /// <summary> /// 베지어 곡선 포인트 리스트 구하기 /// </summary> /// <param name="startPoint">시작점</param> /// <param name="controlPoint1">제어점 1</param> /// <param name="controlPoint2">제어점 2</param> /// <param name="endPoint">종료점</param> /// <param name="pointCount">포인트 수</param> /// <returns>베지어 곡선 포인트 리스트</returns> public List<Point> GetBezierCurvePointList(Point startPoint, Point controlPoint1, Point controlPoint2, Point endPoint, int pointCount) { List<Point> list = new List<Point>(pointCount); for(int i = 0; i < pointCount; i++) { double t = (double)i / (pointCount - 1); double x = (1 - t) * (1 - t) * (1 - t) * startPoint.X + 3 * t * (1 - t) * (1 - t) * controlPoint1.X + 3 * t * t * (1 - t) * controlPoint2.X + t * t * t * endPoint.X; double y = (1 - t) * (1 - t) * (1 - t) * startPoint.Y + 3 * t * (1 - t) * (1 - t) * controlPoint1.Y + 3 * t * t * (1 - t) * controlPoint2.Y + t * t * t * endPoint.Y; list.Add(new Point(x, y)); } return list; } #endregion |
■ 나선형 Point 리스트를 구하는 방법을 보여준다. ▶ 나선형 Point 리스트 구하기 예제 (C#)
1 2 3 4 5 6 |
using System.Collections.Generic; using System.Windows; List<Point> spiralPointList = GetSpiralPointList(new Point(300d, 300d), 100d, 2000d, 20d); |
▶ 나선형 Point 리스트 구하기 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
using System; using System.Collections.Generic; using System.Windows; #region 나선형 Point 리스트 구하기 - GetSpiralPointList(centerPoint, radius, pointCount, reviseCount) /// <summary> /// 나선형 Point 리스트 구하기 /// </summary> /// <param name="centerPoint">중심점</param> /// <param name="radius">반경</param> /// <param name="pointCount">포인트 수</param> /// <param name="reviseCount">수정 수</param> /// <returns>나선형 Point 리스트</returns> public List<Point> GetSpiralPointList(Point centerPoint, double radius, int pointCount, int reviseCount) { List<Point> list = new List<Point>(); for(int i = 0; i < pointCount; i++) { double angle = i * 2d * Math.PI / (pointCount / reviseCount); double scale = radius * (1 - (double) i / pointCount); double x = centerPoint.X + scale * Math.Cos(angle); double y = centerPoint.Y + scale * Math.Sin(angle); list.Add(new Point(x, y)); } return list; } #endregion |
■ GroupStyle 엘리먼트 : HeaderTemplate 속성을 사용해 ListBox 객체에서 그룹 스타일을 설정하는 방법을 보여준다. ▶ 예제 코드 (XAML)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
... <ListBox Name="listBox"> <ListBox.ItemTemplate> ... </ListBox.ItemTemplate> <ListBox.GroupStyle> <GroupStyle> <GroupStyle.HeaderTemplate> <DataTemplate> <TextBlock Margin="6" Foreground="White" Background="DarkGray" FontWeight="Bold" FontSize="12pt" Text="{Binding Path=Name}" /> </DataTemplate> </GroupStyle.HeaderTemplate> </GroupStyle> </ListBox.GroupStyle> </ListBox> ... |
▶ 예제 코드
■ CollectionView 클래스의 Filter 속성을 설정하는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
using System.Collections.ObjectModel; using System.Windows.Data; ObservableCollection<Person> observableCollection = new ObservableCollection<Person>(); ... CollectionView collectionView = new CollectionView(observableCollection); collectionView.Filter = LivingPersionFilter; ... #region 생존자 필터 처리하기 - LivingPersionFilter(value) /// <summary> /// 생존자 필터 처리하기 /// </summary> /// <param name="value">값</param> /// <returns>처리 결과</returns> private bool LivingPersionFilter(object value) { return (value as Person).DeathDate == null; } #endregion |
※ Person 클래스를 예제 클래스로 구체적으로 명시하지 않았다.
■ CollectionView 클래스에서 정렬 순서를 추가하는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
using System.ComponentModel; using System.Windows.Data; #region 정렬 순서 추가하기 - AddSortOrder(collectionView, propertyName, listSortDirection) /// <summary> /// 정렬 순서 추가하기 /// </summary> /// <param name="collectionView">CollectionView 객체</param> /// <param name="propertyName">속성명</param> /// <param name="listSortDirection">리스트 정렬 방향</param> public void AddSortOrder(CollectionView collectionView, string propertyName, ListSortDirection listSortDirection) { collectionView.SortDescriptions.Add(new SortDescription(propertyName, listSortDirection)); } #endregion |
■ ItemsControl 클래스에서 항목을 구하는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
using System.Windows.Controls; #region 항목 구하기 - GetItem<TItem>(itemsControl, itemIndex) /// <summary> /// 항목 구하기 /// </summary> /// <typeparam name="TItem">항목 타입</typeparam> /// <param name="itemsControl">ItemsControl 객체</param> /// <param name="itemIndex">항목 인덱스</param> /// <returns>항목 객체</returns> public TItem GetItem<TItem>(ItemsControl itemsControl, int itemIndex) where TItem : class { return itemsControl.ItemContainerGenerator.ContainerFromItem(itemsControl.Items[itemIndex]) as TItem; } #endregion |
■ CollectionView 클래스에서 정렬 순서를 지우는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
using System.Windows.Data; #region 정렬 순서 지우기 - ClearSortOrder(collectionView) /// <summary> /// 정렬 순서 지우기 /// </summary> /// <param name="collectionView">CollectionView 객체</param> public void ClearSortOrder(CollectionView collectionView) { collectionView.SortDescriptions.Clear(); } #endregion |
■ Button 클래스의 SetResourceReference 메소드를 사용해 리소스를 설정하는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 |
using System.Windows.Controls; ... Button button; ... button.SetResourceReference(Button.StyleProperty, "RedForegroundStyleKey"); |
※ 찾고자 하는 리소스가 존재하지 않는 경우
■ FrameworkElement 클래스의 TryFindResource 메소드를 사용해 리소스를 찾는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 |
using System.Windows; Style style = this.button.TryFindResource("RedForegroundStyleKey") as Style; if(style != null) { this.button.Style = style; } |
※ 찾고자 하는 리소스가 존재하지 않는 경우
■ FrameworkElement 클래스의 FindResource 메소드를 사용해 리소스를 찾는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
using System.Windows; Style style = null; try { style = this.button.FindResource("RedForegroundStyleKey") as Style; } catch { } if(style != null) { this.button.Style = style; } |
※ 찾고자 하는 리소스가 존재하지 않는 경우
■ x:Type 태그 확장을 사용하는 방법을 보여준다. ▶ 예제 코드 (XAML)
1 2 3 |
{x:Type StackPanel} |
■ Binding 태그 확장의 RelativeSource 속성을 사용하는 방법을 보여준다. ▶ TextBlock 자신이 바인딩 소스인 경우 (C#)
1 2 3 |
<TextBlock Text="{Binding RelativeSource={RelativeSource self}, Path=FontFamily}" /> |
▶ TextBlock 기준 1단계 위의
■ VisualTreeHelper 클래스를 사용해 특정 타입의 비주얼을 찾는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 |
using System.Windows; using System.Windows.Media; #region 비주얼 찾기 - FindVisual<T>(source) /// <summary> /// 비주얼 찾기 /// </summary> /// <typeparam name="T">비주얼 타입</typeparam> /// <param name="source">소스 의존 객체</param> /// <returns>비주얼</returns> public TVisual FindVisual<TVisual>(DependencyObject source) where TVisual : class { if(source is TVisual) { return source as TVisual; } for(int i = 0; i < VisualTreeHelper.GetChildrenCount(source); i++) { TVisual child = FindVisual<TVisual>(VisualTreeHelper.GetChild(source, i)); if(child != null) { return child; } } return null; } #endregion |
■ Keyboard 클래스의 IsKeyDown 메소드를 사용해 키 다운 여부를 조사하는 방법을 보여준다. ▶ 예제 코드 (C#)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
using System.Windows; using System.Windows.Input; #region 키 다운 여부 조사하기 - IsKeyDown(key) /// <summary> /// 키 다운 여부 조사하기 /// </summary> /// <param name="key">Key 열거형</param> /// <returns>키 다운 여부</returns> public bool IsKeyDown(Key key) { return Keyboard.IsKeyDown(key); } #endregion |
■ ControlTemplate 엘리먼트의 TargetType 속성을 사용해 Button 엘리먼트를 정의하는 방법을 보여준다. ▶ MainWindow.xaml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 |
<Window x:Class="TestProject.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Width="800" Height="600" Title="ControlTemplate 엘리먼트 : TargetType 속성을 사용해 Button 엘리먼트 정의하기" FontFamily="나눔고딕코딩" FontSize="16"> <Grid> <Button HorizontalAlignment="Center" VerticalAlignment="Center" Padding="20" FontSize="48"> Button with Custom Template <Button.Template> <ControlTemplate TargetType="{x:Type Button}"> <Border Name="border" BorderThickness="3" BorderBrush="Red" Background="{DynamicResource {x:Static SystemColors.ControlLightBrushKey}}"> <TextBlock Name="textBlock" Margin="{TemplateBinding Padding}" FontStyle="Italic" Text="{TemplateBinding Content}" /> </Border> <ControlTemplate.Triggers> <Trigger Property="IsMouseOver" Value="True"> <Setter TargetName="border" Property="CornerRadius" Value="24" /> <Setter TargetName="textBlock" Property="FontWeight" Value="Bold" /> </Trigger> <Trigger Property="IsPressed" Value="True"> <Setter TargetName="border" Property="Background" Value="{DynamicResource {x:Static SystemColors.ControlDarkBrushKey}}" /> </Trigger> </ControlTemplate.Triggers> </ControlTemplate> </Button.Template> </Button> </Grid> </Window> |
※ ControlTemplate 엘리먼트에서 TargetType 속성을 사용하면 TemplateBinding 표현에서
■ DataTrigger 엘리먼트를 사용하는 방법을 보여준다. ▶ MainWindow.xaml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 |
<Window x:Class="TestProject.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Width="800" Height="600" Title="DataTrigger 엘리먼트 사용하기" FontFamily="나눔고딕코딩" FontSize="16"> <StackPanel HorizontalAlignment="Center" VerticalAlignment="Center"> <StackPanel.Resources> <Style TargetType="{x:Type Button}"> <Setter Property="HorizontalAlignment" Value="Center" /> <Setter Property="Margin" Value="10" /> <Setter Property="Width" Value="100" /> <Setter Property="Height" Value="30" /> <Style.Triggers> <DataTrigger Binding="{Binding ElementName=textBox, Path=Text.Length}" Value="0"> <Setter Property="IsEnabled" Value="False" /> </DataTrigger> </Style.Triggers> </Style> </StackPanel.Resources> <TextBox Name="textBox" HorizontalAlignment="Center" Margin="10" Width="300" Height="25" VerticalContentAlignment="Center" /> <Button>버튼 1</Button> <Button>버튼 2</Button> <Button>버튼 3</Button> </StackPanel> </Window> |
TestProject.zip
■ MultiTrigger 엘리먼트를 사용하는 방법을 보여준다. ▶ MainWindow.xaml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
<Window x:Class="TestProject.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Width="800" Height="600" Title="MultiTrigger 엘리먼트 사용하기" FontFamily="나눔고딕코딩" FontSize="16"> <StackPanel HorizontalAlignment="Center" VerticalAlignment="Center"> <StackPanel.Resources> <Style x:Key="normal"> <Setter Property="Control.HorizontalAlignment" Value="Center" /> <Setter Property="Control.Margin" Value="10" /> <Setter Property="Control.Padding" Value="20 10 20 10" /> <Setter Property="Control.FontSize" Value="24" /> <Style.Triggers> <Trigger Property="Button.IsPressed" Value="True"> <Setter Property="Control.Foreground" Value="Red" /> </Trigger> <MultiTrigger> <MultiTrigger.Conditions> <Condition Property="Control.IsMouseOver" Value="True" /> <Condition Property="Button.IsPressed" Value="False" /> </MultiTrigger.Conditions> <Setter Property="Control.FontStyle" Value="Italic" /> <Setter Property="Control.Foreground" Value="Blue" /> </MultiTrigger> </Style.Triggers> </Style> </StackPanel.Resources> <Button Style="{StaticResource normal}">버튼 1</Button> <Button Style="{StaticResource normal}">버튼 2</Button> <Button Style="{StaticResource normal}">버튼 3</Button> </StackPanel> </Window> |
TestProject.zip
■ Trigger 엘리먼트를 사용하는 방법을 보여준다. ▶ 예제 코드 (XAML)
1 2 3 4 5 6 7 8 |
<Style.Triggers> <Trigger Property="Control.IsMouseOver" Value="True"> <Setter Property="Control.FontStyle" Value="Italic" /> <Setter Property="Control.Foreground" Value="Blue" /> </Trigger> </Style.Triggers> |
■ Style 엘리먼트의 BasedOn 속성을 사용해 TargetType 속성 값으로 정의한 버튼 타입 스타일을 상속하는 방법을 보여준다. ▶ MainWindow.xaml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
<Window x:Class="TestProject.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Width="800" Height="600" Title="Style 엘리먼트 : BasedOn 속성을 사용해 TargetType 속성 값으로 정의한 버튼 타입 스타일 상속하기" FontFamily="나눔고딕코딩" FontSize="16"> <Window.Resources> <Style TargetType="{x:Type Button}"> <Setter Property="Control.HorizontalAlignment" Value="Center" /> <Setter Property="Control.Margin" Value="24" /> <Setter Property="Control.FontSize" Value="24" /> <Setter Property="Control.Foreground" Value="Blue" /> </Style> <Style x:Key="HotButtonKey" TargetType="{x:Type Button}" BasedOn="{StaticResource {x:Type Button}}"> <Setter Property="Control.Foreground" Value="Red" /> </Style> </Window.Resources> <StackPanel HorizontalAlignment="Center" VerticalAlignment="Center"> <Button HorizontalAlignment="Center" VerticalAlignment="Center" Margin="10" Padding="10" Content="테스트" /> <Button Style="{StaticResource HotButtonKey}" HorizontalAlignment="Center" VerticalAlignment="Center" Margin="10" Padding="10" Content="테스트" /> </StackPanel> </Window> |
※ TargetType 특성으로
■ Sytle 클래스의 BasedOn 속성을 사용하는 방법을 보여준다. ▶ 예제 코드 (XAML)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<Style x:Key="NormalStyleKey"> <Setter Property="Control.FontSize" Value="24" /> <Setter Property="Control.Foreground" Value="Blue" /> <Setter Property="Control.HorizontalAlignment" Value="Center" /> <Setter Property="Control.Margin" Value="24" /> <Setter Property="Control.Padding" Value="20, 10, 20, 10" /> </Style> <Style x:Key="HotButtonStyleKey" BasedOn="{StaticResource NormalStyleKey}"> <Setter Property="Control.Foreground" Value="Red" /> </Style> |
■ Style 엘리먼트의 TargetType 속성을 사용해 버튼 스타일을 설정하는 방법을 보여준다. ▶ MainWindow.xaml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
<Window x:Class="TestProject.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Width="800" Height="600" Title="Style 엘리먼트 : TargetType 속성을 사용해 버튼 스타일 설정하기" FontFamily="나눔고딕코딩" FontSize="16"> <Window.Resources> <Style TargetType="{x:Type Button}"> <Setter Property="Margin" Value="10" /> <Setter Property="FontSize" Value="24" /> <Setter Property="Foreground" Value="Blue" /> </Style> </Window.Resources> <Grid> <Button HorizontalAlignment="Center" VerticalAlignment="Center" Padding="10" Content="테스트" /> </Grid> </Window> |
※ x:Type 태그 확장을 사용하지 않아도 된다. ※
■ Setter 엘리먼트의 Value 속성 값으로 NULL 값을 설정하는 방법을 보여준다. ▶ 예제 코드 (XAML)
1 2 3 |
<Setter Property="Control.Foreground" Value="{x:Null}" /> |