Geometry 개요
업데이트: 2007년 11월
이 개요에서는 WPF(Windows Presentation Foundation) Geometry 클래스를 사용하여 도형을 설명하는 방법에 대해 설명합니다. 이 항목에서는 Geometry 개체와 Shape 요소의 차이점도 비교합니다.
이 항목에는 다음 단원이 포함되어 있습니다.
- Geometry란?
- 기하 도형과 도형 비교
- Geometry를 사용하는 공용 속성
- 단순한 기하 도형 형식
- 경로 기하 도형
- 복합 기하 도형
- 결합된 기하 도형
- Freezable 기능
- 기타 Geometry 기능
- 관련 항목
Geometry란?
Geometry 클래스와 이 클래스에서 파생되는 EllipseGeometry, PathGeometry, CombinedGeometry 등의 클래스를 사용하면 2차원 도형의 기하 도형을 설명할 수 있습니다. 이러한 기하학적 설명은 도형을 정의하여 화면 그리기, 적중 테스트 및 클립 영역 정의 등의 여러 용도에 사용됩니다. 기하 도형을 사용하여 애니메이션 경로를 정의할 수도 있습니다.
Geometry 개체는 사각형 및 원과 같은 단순 영역이나 둘 이상의 기하 도형 개체로 이루어진 복합 영역일 수 있습니다. 원호와 곡선을 설명하는 데 사용할 수 있는 PathGeometry 및 StreamGeometry 클래스를 사용하여 보다 복잡한 복합 기하 도형을 만들 수 있습니다.
Geometry는 Freezable 형식이므로 Geometry 개체는 몇 가지 특수한 기능을 제공합니다. 예를 들어 리소스로 선언하거나, 여러 개체 간에 공유하거나, 읽기 전용으로 설정하여 성능을 향상할 수 있으며, 복제하거나, 스레드로부터 안전하게 보호할 수 있습니다. Freezable 개체에서 제공하는 여러 기능에 대한 자세한 내용은 Freezable 개체 개요를 참조하십시오.
기하 도형과 도형 비교
Geometry 및 Shape 클래스는 모두 2차원 도형을 설명한다는 점에서 유사한 듯 보이지만(예를 들어 EllipseGeometry 및 Ellipse 비교) 중요한 차이점이 있습니다.
그 중 하나는 Geometry 클래스는 Freezable 클래스에서 상속하는 반면 Shape 클래스는 FrameworkElement에서 상속합니다. Shape 개체는 요소이므로 자체를 렌더링하고 레이아웃 시스템에 참여할 수 있지만 Geometry 개체는 그럴 수 없습니다.
Shape 개체는 Geometry 개체보다 더 쉽게 사용할 수 있지만 Geometry 개체는 더욱 다양한 방식으로 사용할 수 있습니다. Shape 개체는 2차원 그래픽을 렌더링하는 데 사용되는 반면 Geometry 개체는 2차원 그래픽의 기하학적 영역을 정의하거나, 클리핑 영역을 정의하거나, 적중 회수 테스트 영역을 정의하는 등에 사용할 수 있습니다.
경로 도형
하나의 Shape인 Path 클래스에서는 실제로 Geometry를 사용하여 해당 콘텐츠를 설명합니다. Geometry를 사용하여 Path의 Data 속성을 설정하고 해당 Fill 및 Stroke 속성을 설정하면 Geometry를 렌더링할 수 있습니다.
Geometry를 사용하는 공용 속성
앞의 단원에서 설명한 바와 같이 다른 개체에서 도형 그리기, 애니메이션 효과 적용 및 클리핑과 같은 다양한 용도로 Geometry 개체를 사용할 수 있습니다. 다음 표에서는 Geometry 개체를 사용하는 속성이 있는 여러 클래스를 보여 줍니다.
형식 |
속성 |
---|---|
단순한 기하 도형 형식
모든 기하 도형의 기본 클래스는 추상 클래스 Geometry입니다. Geometry 클래스에서 파생되는 클래스는 대략 단순 기하 도형, 경로 기하 도형 및 복합 기하 도형의 세 가지 범주로 묶을 수 있습니다.
단순 기하 도형 클래스는 LineGeometry, RectangleGeometry 및 EllipseGeometry를 포함하며 선, 사각형, 원과 같은 기본적인 기하학 도형을 만드는 데 사용됩니다.
LineGeometry는 선의 시작점과 끝점을 지정하여 정의합니다.
RectangleGeometry는 사각형의 상대적 위치와 높이 및 너비를 지정하는 Rect 구조체를 사용하여 정의합니다. RadiusX 및 RadiusY속성을 설정하여 모퉁이가 둥근 사각형을 만들 수 있습니다.
EllipseGeometry는 중심점, x 반지름 및 y 반지름으로 정의합니다. 다음 예제에서는 렌더링 및 클리핑하기 위한 단순 기하 도형을 만드는 방법을 보여 줍니다.
이와 같은 도형 및 보다 복잡한 도형을 PathGeometry를 사용하거나 기하 도형 개체를 결합하여 만들 수 있지만 이러한 클래스를 사용하면 이러한 기본적인 기하 도형을 더 간단하게 만들 수 있습니다.
다음 예제에서는 LineGeometry를 만들고 렌더링하는 방법을 보여 줍니다. 앞에서 설명한 대로 Geometry 개체는 자신을 그릴 수 없으므로 이 예제에서는 Path 도형을 사용하여 선을 렌더링합니다. 선에는 면적이 없으므로 Path의 Fill 속성을 설정해도 아무 영향이 없습니다. 대신 Stroke 및 StrokeThickness 속성만 지정합니다. 다음 그림에서는 이 예제를 실행한 결과를 보여 줍니다.
(10,20)에서 (100,130) 사이에 그린 LineGeometry
<Path Stroke="Black" StrokeThickness="1" >
<Path.Data>
<LineGeometry StartPoint="10,20" EndPoint="100,130" />
</Path.Data>
</Path>
LineGeometry myLineGeometry = new LineGeometry();
myLineGeometry.StartPoint = new Point(10,20);
myLineGeometry.EndPoint = new Point(100,130);
Path myPath = new Path();
myPath.Stroke = Brushes.Black;
myPath.StrokeThickness = 1;
myPath.Data = myLineGeometry;
다음 예제에서는 EllipseGeometry를 만들고 렌더링하는 방법을 보여 줍니다. 이 예제에서는 EllipseGeometry의 Center를 점 50,50으로 설정하고 x 반지름 및 y 반지름을 모두 50으로 설정하여 지름이 100인 원을 만듭니다. Path 요소의 Fill 채우기 속성에 값(여기서는 Gold)을 할당하여 타원의 내부를 그립니다. 다음 그림에서는 이 예제를 실행한 결과를 보여 줍니다.
(50,50)에 그린 EllipseGeometry
<Path Fill="Gold" Stroke="Black" StrokeThickness="1">
<Path.Data>
<EllipseGeometry Center="50,50" RadiusX="50" RadiusY="50" />
</Path.Data>
</Path>
EllipseGeometry myEllipseGeometry = new EllipseGeometry();
myEllipseGeometry.Center = new Point(50, 50);
myEllipseGeometry.RadiusX = 50;
myEllipseGeometry.RadiusY = 50;
Path myPath = new Path();
myPath.Fill = Brushes.Gold;
myPath.Stroke = Brushes.Black;
myPath.StrokeThickness = 1;
myPath.Data = myEllipseGeometry;
다음 예제에서는 RectangleGeometry를 만들고 렌더링하는 방법을 보여 줍니다. 사각형의 위치와 치수는 Rect 구조체를 사용하여 정의합니다. 위치는 50,50으로 지정하고 높이와 너비를 모두 25로 지정하여 정사각형을 만듭니다. 다음 그림에서는 이 예제를 실행한 결과를 보여 줍니다.
50,50에 그린 RectangleGeometry
<Path Fill="LemonChiffon" Stroke="Black" StrokeThickness="1">
<Path.Data>
<RectangleGeometry Rect="50,50,25,25" />
</Path.Data>
</Path>
RectangleGeometry myRectangleGeometry = new RectangleGeometry();
myRectangleGeometry.Rect = new Rect(50,50,25,25);
Path myPath = new Path();
myPath.Fill = Brushes.LemonChiffon;
myPath.Stroke = Brushes.Black;
myPath.StrokeThickness = 1;
myPath.Data = myRectangleGeometry;
다음 예제에서는 EllipseGeometry를 이미지의 클리핑 영역으로 사용하는 방법을 보여 줍니다. Image 개체는 Width는 200 및 Height는 150로 지정하여 정의합니다. RadiusX 값은 100, RadiusY 값은 75, Center 값은 100,75인 EllipseGeometry를 이미지의 Clip 속성으로 설정합니다. 그러면 타원 영역 내에 있는 이미지 부분만 표시됩니다. 다음 그림에서는 이 예제를 실행한 결과를 보여 줍니다.
Image 컨트롤을 클리핑하는 데 사용된 EllipseGeometry
<Image
Source="sampleImages\Waterlilies.jpg"
Width="200" Height="150" HorizontalAlignment="Left">
<Image.Clip>
<EllipseGeometry
RadiusX="100"
RadiusY="75"
Center="100,75"/>
</Image.Clip>
</Image>
// Create the image to clip.
Image myImage = new Image();
Uri imageUri =
new Uri(@"C:\\Documents and Settings\\All Users\\Documents\My Pictures\\Sample Pictures\\Water lilies.jpg", UriKind.Relative);
myImage.Source = new BitmapImage(imageUri);
myImage.Width = 200;
myImage.Height = 150;
myImage.HorizontalAlignment = HorizontalAlignment.Left;
// Use an EllipseGeometry to define the clip region.
EllipseGeometry myEllipseGeometry = new EllipseGeometry();
myEllipseGeometry.Center = new Point(100, 75);
myEllipseGeometry.RadiusX = 100;
myEllipseGeometry.RadiusY = 75;
myImage.Clip = myEllipseGeometry;
경로 기하 도형
PathGeometry 클래스 및 이에 해당하는 간단한 StreamGeometry 클래스는 원호, 곡선 및 선으로 구성된 여러 복잡한 그림을 설명할 수 있는 방법을 제공합니다.
PathGeometry의 핵심은 PathFigure 개체의 컬렉션입니다. 이와 같은 이름이 지정된 까닭은 각 그림이 PathGeometry에서 개별 도형을 설명하기 때문입니다. 각 PathFigure 자체는 각각 그림의 세그먼트를 설명하는 하나 이상의 PathSegment 개체로 구성됩니다.
세그먼트에는 여러 가지 형식이 있습니다.
세그먼트 형식 |
설명 |
예제 |
---|---|---|
두 점 사이에 타원형 원호를 만듭니다. |
||
두 점 사이에 입방형 3차원 곡선을 만듭니다. |
||
두 점 사이에 선을 만듭니다. |
||
일련의 입방형 3차원 곡선을 만듭니다. |
PolyBezierSegment 형식 페이지를 참조하십시오. |
|
일련의 선을 만듭니다. |
PolyLineSegment 형식 페이지를 참조하십시오. |
|
일련의 정방형 3차원 곡선을 만듭니다. |
PolyQuadraticBezierSegment 페이지를 참조하십시오. |
|
정방형 3차원 곡선을 만듭니다. |
PathFigure의 세그먼트는 각 세그먼트의 끝점이 다음 세그먼트의 시작점이 되어 하나의 기하학적 도형으로 결합됩니다. PathFigure의 StartPoint 속성은 첫 번째 세그먼트가 그려지는 점을 지정합니다. 이후의 각 세그먼트는 이전 세그먼트의 끝점에서 시작됩니다. 예를 들어 10,50에서 10,150까지 이어지는 수직선을 정의하려면 StartPoint 속성을 10,50으로 설정하고 Point 속성이 10,150으로 설정된 LineSegment를 만듭니다.
다음 예제에서는 LineSegment를 사용하여 단일 PathFigure로 구성되는 단순 PathGeometry를 만들고 Path 요소를 사용하여 이를 표시합니다. PathFigure 개체의 StartPoint를 10,20으로 설정하고 LineSegment를 끝점 100,130으로 정의합니다. 다음 그림에서는 이 예제에서 만든 PathGeometry를 보여 줍니다.
단일 LineSegment를 포함하는 PathGeometry
<Path Stroke="Black" StrokeThickness="1">
<Path.Data>
<PathGeometry>
<PathGeometry.Figures>
<PathFigure StartPoint="10,20">
<PathFigure.Segments>
<LineSegment Point="100,130"/>
</PathFigure.Segments>
</PathFigure>
</PathGeometry.Figures>
</PathGeometry>
</Path.Data>
</Path>
// Create a figure that describes a
// line from (10,20) to (100,130).
PathFigure myPathFigure = new PathFigure();
myPathFigure.StartPoint = new Point(10,20);
myPathFigure.Segments.Add(
new LineSegment(new Point(100,130),
true /* IsStroked */ ));
/// Create a PathGeometry to contain the figure.
PathGeometry myPathGeometry = new PathGeometry();
myPathGeometry.Figures.Add(myPathFigure);
// Display the PathGeometry.
Path myPath = new Path();
myPath.Stroke = Brushes.Black;
myPath.StrokeThickness = 1;
myPath.Data = myPathGeometry;
이 예제를 앞의 LineGeometry 예제와 비교해 보는 것이 좋습니다. PathGeometry에 사용된 구문이 단순 LineGeometry에 사용된 구문보다 훨씬 자세하고 이 경우 LineGeometry 클래스를 사용하는 것이 실용적일 수 있지만 PathGeometry의 자세한 구문에서는 매우 상세하고 복잡한 기하학적 영역을 고려합니다.
더욱 복잡한 기하 도형은 PathSegment 개체를 조합하여 만들 수 있습니다.
다음 예제에서는 BezierSegment, LineSegment 및 ArcSegment를 사용하여 도형을 만듭니다. 이 예제에서는 먼저 이전 세그먼트의 끝점인 시작점, 끝점(Point3) 및 두 개의 제어점(Point1 및 Point2)의 네 점을 정의하여 입방형 3차원 곡선을 만듭니다. 입방형 3차원 곡선의 두 제어점은 자석과 같은 역할을 하여 직선이 될 수 있는 부분을 서로 끌어당겨 곡선을 만듭니다. 첫 번째 제어점인 Point1은 곡선의 시작 부분에 영향을 주고, 두 번째 제어점인 Point2는 곡선의 끝 부분에 영향을 줍니다.
이 예제에서는 그런 다음 앞에 있는 BezierSegment의 끝점과 LineSegment 속성으로 지정한 점 사이에 LineSegment를 그립니다.
이 예제에서는 그런 다음 앞에 있는 LineSegment의 끝점과 Point 속성으로 지정한 점 사이에 ArcSegment를 그립니다. 또한 이 예제에서는 원호의 x 및 y 반지름(Size), 회전 각도(RotationAngle), 결과 원호의 각도 크기를 표시하는 플래그(IsLargeArc) 및 원호를 그리는 방향을 표시하는 값(SweepDirection)을 지정합니다. 다음 그림에서는 이 예제에서 만든 도형을 보여 줍니다.
PathGeometry
<Path Stroke="Black" StrokeThickness="1" >
<Path.Data>
<PathGeometry>
<PathGeometry.Figures>
<PathFigure StartPoint="10,50">
<PathFigure.Segments>
<BezierSegment
Point1="100,0"
Point2="200,200"
Point3="300,100"/>
<LineSegment Point="400,100" />
<ArcSegment
Size="50,50" RotationAngle="45"
IsLargeArc="True" SweepDirection="Clockwise"
Point="200,100"/>
</PathFigure.Segments>
</PathFigure>
</PathGeometry.Figures>
</PathGeometry>
</Path.Data>
</Path>
// Create a figure.
PathFigure myPathFigure = new PathFigure();
myPathFigure.StartPoint = new Point(10,50);
myPathFigure.Segments.Add(
new BezierSegment(
new Point(100,0),
new Point(200,200),
new Point(300,100),
true /* IsStroked */ ));
myPathFigure.Segments.Add(
new LineSegment(
new Point(400,100),
true /* IsStroked */ ));
myPathFigure.Segments.Add(
new ArcSegment(
new Point(200,100),
new Size(50,50),
45,
true, /* IsLargeArc */
SweepDirection.Clockwise,
true /* IsStroked */ ));
/// Create a PathGeometry to contain the figure.
PathGeometry myPathGeometry = new PathGeometry();
myPathGeometry.Figures.Add(myPathFigure);
// Display the PathGeometry.
Path myPath = new Path();
myPath.Stroke = Brushes.Black;
myPath.StrokeThickness = 1;
myPath.Data = myPathGeometry;
PathGeometry 내에 여러 PathFigure 개체를 사용하여 훨씬 더 복잡한 기하 도형을 만들 수 있습니다.
다음 예제에서는 각각 여러 PathSegment 개체를 포함하는 두 개의 PathFigure 개체를 사용하여 PathGeometry를 만듭니다. 위의 예제에 있는 PathFigure와 PolyLineSegment 및 QuadraticBezierSegment를 포함하는 PathFigure를 사용합니다. PolyLineSegment는 점 배열로 정의하고 QuadraticBezierSegment는 제어점과 끝점으로 정의합니다. 다음 그림에서는 이 예제에서 만든 도형을 보여 줍니다.
여러 그림을 포함하는 PathGeometry
<Path Stroke="Black" StrokeThickness="1" >
<Path.Data>
<PathGeometry>
<PathGeometry.Figures>
<PathFigure StartPoint="10,50">
<PathFigure.Segments>
<BezierSegment
Point1="100,0"
Point2="200,200"
Point3="300,100"/>
<LineSegment Point="400,100" />
<ArcSegment
Size="50,50" RotationAngle="45"
IsLargeArc="True" SweepDirection="Clockwise"
Point="200,100"/>
</PathFigure.Segments>
</PathFigure>
<PathFigure StartPoint="10,100">
<PathFigure.Segments>
<PolyLineSegment Points="50,100 50,150" />
<QuadraticBezierSegment Point1="200,200" Point2="300,100"/>
</PathFigure.Segments>
</PathFigure>
</PathGeometry.Figures>
</PathGeometry>
</Path.Data>
</Path>
PathGeometry myPathGeometry = new PathGeometry();
// Create a figure.
PathFigure pathFigure1 = new PathFigure();
pathFigure1.StartPoint = new Point(10,50);
pathFigure1.Segments.Add(
new BezierSegment(
new Point(100,0),
new Point(200,200),
new Point(300,100),
true /* IsStroked */ ));
pathFigure1.Segments.Add(
new LineSegment(
new Point(400,100),
true /* IsStroked */ ));
pathFigure1.Segments.Add(
new ArcSegment(
new Point(200,100),
new Size(50,50),
45,
true, /* IsLargeArc */
SweepDirection.Clockwise,
true /* IsStroked */ ));
myPathGeometry.Figures.Add(pathFigure1);
// Create another figure.
PathFigure pathFigure2 = new PathFigure();
pathFigure2.StartPoint = new Point(10,100);
Point[] polyLinePointArray =
new Point[]{ new Point(50, 100), new Point(50, 150)};
PolyLineSegment myPolyLineSegment = new PolyLineSegment();
myPolyLineSegment.Points =
new PointCollection(polyLinePointArray);
pathFigure2.Segments.Add(myPolyLineSegment);
pathFigure2.Segments.Add(
new QuadraticBezierSegment(
new Point(200,200),
new Point(300,100),
true /* IsStroked */ ));
myPathGeometry.Figures.Add(pathFigure2);
// Display the PathGeometry.
Path myPath = new Path();
myPath.Stroke = Brushes.Black;
myPath.StrokeThickness = 1;
myPath.Data = myPathGeometry;
StreamGeometry
PathGeometry 클래스처럼 StreamGeometry는 곡선, 원호 및 선을 포함할 수 있는 복잡한 기하 도형을 정의합니다. 그러나 PathGeometry와 달리 StreamGeometry의 콘텐츠에서는 데이터 바인딩, 애니메이션 또는 수정을 지원하지 않습니다. 복잡한 기하 도형을 설명해야 하지만 데이터 바인딩, 애니메이션 및 수정에 대한 지원에 따른 오버헤드를 원하지 않는 경우 StreamGeometry를 사용합니다. StreamGeometry 클래스는 효율성으로 인해 표시기(adorner)를 설명하기에 적합합니다.
예제를 보려면 방법: StreamGeometry를 사용하여 도형 만들기를 참조하십시오.
경로 태그 구문
PathGeometry 및 StreamGeometry 형식에서는 특수한 일련의 이동 및 그리기 명령을 사용하여 XAML(Extensible Application Markup Language) 특성 구문을 지원합니다. 자세한 내용은 경로 태그 구문을 참조하십시오.
복합 기하 도형
복합 기하 도형 개체는 GeometryGroup 및 CombinedGeometry를 사용하여 만들거나 정적 Geometry 메서드 Combine을 호출하여 만들 수 있습니다.
CombinedGeometry 개체 및 Combine 메서드는 부울 연산을 수행하여 두 기하 도형에서 정의하는 영역을 결합합니다. 영역이 없는 Geometry 개체는 삭제됩니다. 이러한 두 개의 기하 도형도 복합 기하 도형이 될 수 있지만 두 개의 Geometry 개체만 결합할 수 있습니다.
GeometryGroup 클래스는 포함하는 Geometry 개체를 해당 영역을 결합하지 않고 통합합니다. 원하는 수의 Geometry 개체를 GeometryGroup에 추가할 수 있습니다. 예제를 보려면 방법: 복합 도형 만들기를 참조하십시오.
GeometryGroup 개체를 사용하면 결합 작업을 수행하지 않으므로 CombinedGeometry 개체나 Combine 메서드를 사용하는 것보다 성능상 이점이 있습니다.
결합된 기하 도형
앞의 단원에서 설명한 바와 같이 CombinedGeometry 개체 및 Combine 메서드는 자신들이 포함하는 기하 도형에서 정의하는 영역을 결합합니다. GeometryCombineMode 열거형은 기하 도형을 결합하는 방법을 지정합니다. GeometryCombineMode 속성의 가능한 값은 Union, Intersect, Exclude 및 Xor입니다.
다음 예제에서는 공용 구조체의 결합 모드를 사용하여 CombinedGeometry를 정의합니다. Geometry1 및 Geometry2를 모두 반지름은 같지만 중심이 50만큼 오프셋된 원으로 정의합니다.
<Path Stroke="Black" StrokeThickness="1" Fill="#CCCCFF">
<Path.Data>
<!-- Combines two geometries using the union combine mode. -->
<CombinedGeometry GeometryCombineMode="Union">
<CombinedGeometry.Geometry1>
<EllipseGeometry RadiusX="50" RadiusY="50" Center="75,75" />
</CombinedGeometry.Geometry1>
<CombinedGeometry.Geometry2>
<EllipseGeometry RadiusX="50" RadiusY="50" Center="125,75" />
</CombinedGeometry.Geometry2>
</CombinedGeometry>
</Path.Data>
</Path>
다음 예제에서는 Xor의 결합 모드를 사용하여 CombinedGeometry를 정의합니다. Geometry1 및 Geometry2를 모두 반지름은 같지만 중심이 50만큼 오프셋된 원으로 정의합니다.
<Path Stroke="Black" StrokeThickness="1" Fill="#CCCCFF">
<Path.Data>
<!-- Combines two geometries using the XOR combine mode. -->
<CombinedGeometry GeometryCombineMode="Xor">
<CombinedGeometry.Geometry1>
<EllipseGeometry RadiusX="50" RadiusY="50" Center="75,75" />
</CombinedGeometry.Geometry1>
<CombinedGeometry.Geometry2>
<EllipseGeometry RadiusX="50" RadiusY="50" Center="125,75" />
</CombinedGeometry.Geometry2>
</CombinedGeometry>
</Path.Data>
</Path>
다른 예제를 보려면 방법: 복합 도형 만들기 및 방법: 결합된 기하 도형 만들기를 참조하십시오.
Freezable 기능
Geometry 클래스는 Freezable 클래스에서 상속되므로 몇 가지 특수한 기능을 제공합니다. 예를 들어 Geometry 개체를 리소스 개요에서와 같이 선언하거나, 여러 개체 간에 공유하거나, 읽기 전용으로 설정하여 성능을 향상시킬 수 있으며, 복제하거나, 스레드로부터 안전하게 보호할 수 있습니다. Freezable 개체에서 제공하는 여러 기능에 대한 자세한 내용은 Freezable 개체 개요를 참조하십시오.
기타 Geometry 기능
Geometry 클래스에서는 다음과 같은 유용한 유틸리티 메서드를 제공합니다.
FillContains - Geometry에 다른 Geometry가 포함되어 있는지 여부를 확인합니다.
StrokeContains - Geometry의 스트로크에 지정한 점이 포함되는지 여부를 확인합니다.
전체 메서드 목록을 보려면 Geometry 클래스를 참조하십시오.