Quartz 2D编程指南(3)路径(Paths)

Paths 

路径定义了一个或多个形状,或是子路径。一个子路径可由直线,曲线,或者同时由两者构成。它可以是开放的,也可以是闭合的。一个子路径可以是简单的形状,如线、圆、矩形、星形;也可以是复杂的形状,如山脉的轮廓或者是涂鸦。图3-1显示了一些我们可以创建的路径。左上角的直线可以是虚线;直线也可以是实线。上边中间的路径是由多条曲线组成的开放路径。右上角的同心圆填充了颜色,但没有描边。左下角的加利福尼亚州是闭合路径,由许多曲线和直线构成,且对路径进行填充和描边。两个星形阐明了填充路径的两种方式,我们将在本章详细描述。

Figure 3-1  Quartz
supports path-based drawing

在本章中,我们将学习如何构建路径,如何对路径进行填充和描边,及影响路径表现形式的参数。

Path Creation and Path Painting

路径创建及路径绘制是两个独立的工作。首先我们先创建路径。当我们需要渲染路径时,我们需要使用Quartz来绘制它。正如图3-1中所示,我们可以选择对路径进行描边,填充路径,或同时进行这两种操作。我们同样可以将其它对象绘制到路径所表示的范围内,即对对象进行裁减。

图3-2绘制了一个路径,该路径包含两个子路径。左边的子路径是一个矩形,右边的子路径是由直线和曲线组成的抽象形状。两个子路径都进行了填充及描边(stroked)。

Figure 3-2  A
path that contains two shapes, or subpaths

图3-3显示了多条独立绘制的路径。每个路径饮食随机生成的曲线,一些进行填充,另一些进行了描边。这些路径都包含在一个圆形裁减区域内。

Figure 3-3  A clipping area constrains drawing

The Building Blocks

子路径是由直线、弧和曲线构成的。Quartz同样也提供了简便的函数用于添加矩形或椭圆等形状。点也是路径最基本的构建块,因为点定义了形状的起始点与终止点。

Points

点由x, y坐标值定义,用于在用户空间指定一个位置。我们可以调用函数CGContextMoveToPoint 来为新的子路径指定起始点。Quartz跟踪当前点,用于记录路径构建过程中最新的位置。例如,如果调用函数CGContextMoveToPoint并设置位置为(10,10),即将当前点移动到位置(10,10)。如果在水平位置绘制50个单位长度的直线,则直线的终点为(60,10),该点变成当前点。直线、弧和曲线总是从当前点开始绘制。

大多数时候我们通过传递(x, y)值给Quartz函数来指定一个点。一些函数需要我们传递一个 CGPoint数据结构,该结构包含两个浮点值。

Lines

直线由两个端点定义。起始点通常是当前点,所以创建直线时,我们只需要指定终止点。我们使用函数CGContextAddLineToPoint 来添加一条直线到子路径中。

我们可以调用CGContextAddLines.函数添加一系列相关的直线到子路径中。我们传递一个点数组给这个函数。第一个点必须是第一条直线的起始点;剩下的点是端点。Quartz从第一个点开始绘制一个新子路径,然后每两个相邻点连接成一条线段。

Arcs

弧是圆弧段。Quartz提供了两个函数来创建弧。函数CGContextAddArc 从圆中来创建一个曲线段。我们指定一个圆心,半径和放射角(以弧度为单位)。放射角为2PI时,创建的是一个圆。图3-4显示了多个独立的路径。每个路径都包含一个随机生成的圆;一些是填充的,另一些是描边的。

Figure 3-4  Multiple
paths; each path contains a randomly generated circle

函数CGContextAddArcToPoint 用于为矩形创建内切弧的场景。Quartz使用我们提供的端点创建两条正切线。同样我们需要提供圆的半径。弧心是两条半径的交叉点,每条半径都与相应的正切线垂直。弧的两个端点是正切线的正切点,如图3-5所示。红色的部分是实际绘制的部分。

Figure 3-5  Defining
an arc with two tangent lines and a radius

如果当前路径已经包含了一个子路径,Quartz将追加一条从当前点到弧的起始点的直线段。如果当前路径为空,Quartz将创建一个新的子路径,该子路径从弧的起始点开始,而不添加初始的直线段。

curves

二次与三次Bezier曲线是代数曲线,可以指定任意的曲线形状。曲线上的点通过一个应用于起始、终点及一个或多个控制点的多项式计算得出。这种方式定义的形状是向量图的基础。这个公式比将位数组更容易存储,并且曲线可以在任何分辨下重新创建。

图3-6显示了一些路径的曲线。每条路径包含一条随机生成的曲线;一些是填充的,另一些是描边的

Figure 3-6  Multiple
paths; each path contains a randomly generated curve

我们使用函数 CGContextAddCurveToPoint将Bezier曲线连接到当前点,并传递控制点和端点作为参数,如图3-7所示。两个控制点的位置决定了曲线的形状。如果两个控制点都在两个端点上面,则曲线向上凸起。如果两个控制点都在两个端点下面,则曲线向下凹。如果第二个控制点比第一个控制点离得当前点近,则曲线自交叉,创建了一个回路。

Figure 3-7  A
cubic Bézier curve uses two control points

我们能够调用函数CGContextAddQuadCurveToPoint来创建Bezier曲线,并传递端点及一个控制点,如图3-8所示,由于使用相同的端点和不同的控制点显示的2种结果。控制点决定了曲线弯曲的方向,由于只使用一个控制点,所以无法创建出许多有趣的曲线。例如我们无法使用一个单一的控制点创建出交叉的曲线。

Figure 3-8  A
quadratic Bézier curve uses one control point

Closing a Subpath

我们可以调用函数CGContextClosePath来关闭当前子路径。该函数用一条直接来连接当前点与起始点,以使路径闭合。起始与终点重合的直线、弧和曲线并不自动闭合路径,我们必须调用CGContextClosePath来闭合路径。

Quartz的一些函数将路径的子路径看成是闭合的。这些函数显示地添加一条直线来闭合 子路径,如同调用了CGContextClosePath函数。

在闭合一条子路径后,如果程序再添加直线、弧或曲线到路径,Quartz将在闭合的子路径的起点开始创建一个新的子路径。

Ellipses

椭圆是一种特殊的圆。椭圆是通过定义两个焦点,在平面内所有与这两个焦点的距离之和相等的点所构成的图形。图3-9显示了一些独立的路径。每个路径都包含一个随机生成的椭圆;一些进行了填充,另一边进行了描边。

Figure 3-9  Multiple paths; each path contains a randomly generated ellipse

我们可以调用CGContextAddEllipseInRect.函数来添加一个椭圆到当前路径。我们提供一个矩形来定义一个椭圆。Quartz利用一系列的Bezier曲线来模拟椭圆。椭圆的中心就是矩形的中心。如果矩形的宽与高相等,则椭圆变成了圆,且圆的半径为矩形宽度的一半。如果矩形的宽与高不相等,则定义了椭圆的长轴与短轴。

添加到路径中的椭圆开始于一个move-to操作,结束于一个close-subpath操作,所有的移动方向都是顺时针。

Rectangles

我们可以调用CGContextAddRect来添加一个矩形到当前路径中,并提供一个CGRect 结构体(包含矩形的原点及大小)作为参数。

添加到路径的矩形开始于一个move-to操作,结束于一个close-subpath操作,所有的移动方向都是逆时针方向。

我们也可能调用CGContextAddRects函数来添加一系列的矩形到当前路径,并传递一个CGRect结构体的数组。图3-10显示了一些独立的路径。每个路径包含一个随机生成的矩形;一些进行了填充,另一边进行了描边。

Figure 3-10  Multiple
paths; each path contains a randomly generated rectangle

Creating a Path

当我们需要在一个图形上下文中构建一个路径时,我们需要调用CGContextBeginPath 来标记Quartz。然后,我们调用函数CGContextMovePoint来设置每一个图形或子路径的起始点。在构建起始点后,我们可以添加直线、弧、曲线。记住如下规则:

1:在开始绘制路径前,调用函数CGContextBeginPath;

2:直线、弧、曲线开始于当前点。空路径没有当前点;我们必须调用CGContextMoveToPoint来设置第一个子路径的起始点,或者调用一个便利函数来隐式地完成该任务。

3:如果想要闭合当前子路径,调用函数CGContextClosePath。随后路径将开始一个新的子路径,即使我们不显示设置一个新的起始点。

4:当绘制弧时,Quartz将在当前点与弧的起始点间绘制一条直线。

5:添加椭圆和矩形的Quartz程序将在路径中添加新的闭合子路径。

6:我们必须调用绘制函数来填充或者描边一条路径,因为创建路径时并不会绘制路径。更多:See Painting
a Path

在绘制路径后,将清空图形上下文。我们也许想保留路径,特别是在绘制复杂场景时,我们需要反复使用。基于此,Quartz提供了两个数据类型来创建可复用路径—CGPathRefCGMutablePathRef。我们可以调用函数CGPathCreateMutable 来创建可变的CGPath对象,并可向该对象添加直线、弧、曲线和矩形。Quartz提供了一个类似于操作图形上下文的CGPath的函数集合。这些路径函数操作CGPath对象,而不是图形上下文。这些函数包括:

CGPathCreateMutable,
which replacesCGContextBeginPath

CGPathMoveToPoint,
which replaces CGContextMoveToPoint

CGPathAddLineToPoint,
which replaces CGContextAddLineToPoint

CGPathAddCurveToPoint,
which replaces CGContextAddCurveToPoint

CGPathAddEllipseInRect,
which replaces CGContextAddEllipseInRect

CGPathAddArc,
which replaces CGContextAddArc

CGPathAddRect,
which replaces CGContextAddRect

CGPathCloseSubpath,
which replaces CGContextClosePath

如果想要添加一个路径到图形上下文,可以调用CGContextAddPath。路径将保留在图形上下文中,直到Quartz绘制它。我们可以调用CGContextAddPath再次添加路径。

Painting a Path

我们可以绘制填充或描边的路径。描边(Stroke)是绘制路径的边框。填充是绘制路径包含的区域。Quartz提供了函数来填充或描边路径。描边线的属性(宽度、颜色等),填充色及Quartz用于计算填充区域的方法都是图形状态的一部分。(see Graphics
States
)

Parameters That Affect Stroking

我们可以使用表3-1中的属性来决定如何对路径进行描边操作。这些属性是图形上下文的一部分,这意味着我们设置的值将会影响到后续的描边操作,直到我们设置参数为其它的值。

          Table
3-1  Parameters that affect how Quartz strokes the current path

Parameter


Function to set parameter value


Line width


CGContextSetLineWidth


Line join


CGContextSetLineJoin


Line cap


CGContextSetLineCap


Miter limit


CGContextSetMiterLimit


Line dash pattern


CGContextSetLineDash


Stroke color space


CGContextSetStrokeColorSpace


Stroke color


CGContextSetStrokeColorCGContextSetStrokeColorWithColor


Stroke pattern


CGContextSetStrokePattern

linewidth是线的总宽度,单位是用户空间单元。

linejoin属性指定如何绘制线段间的联接点。Quartz支持表3-2中描述的联接样式。

Table 3-2  Line join styles

Style


Appearance


Description


Miter join



Quartz extends the outer edges of the strokes for the two segments until they meet at an angle, as in a picture frame. If the segments meet at too sharp an angle, a bevel join is used instead. A segment is too sharp if the length of the miter divided by the
line width is greater than the miter limit.


Round join



Quartz draws a semicircular arc with a diameter equal to the line width around the endpoint. The enclosed area is filled in.


Bevel join



Quartz finishes the two segments with butt caps. The resulting notch beyond the ends of the segments is filled with a triangle.

linecap指定如何绘制直线的端点。Quartz支持表3-3所示的线帽类型。默认的是butt
cap。

Table 3-3  Line cap styles

Style


Appearance


Description


Butt cap



Quartz squares off the stroke at the endpoint of the path. There is no projection beyond the end of the path.


Round cap



Quartz draws a circle with a diameter equal to the line width around the point where the two segments meet, producing a rounded corner. The enclosed area is filled in.


Projecting square cap



Quartz extends the stroke beyond the endpoint of the path for a distance equal to half the line width. The extension is squared off.

闭合路径将起始点看作是一个联接点;起始点同样也使用选定的直线连接方法进行渲染。如果通过添加一条连接到起始点的直线来闭合路径,则路径的两个端点都使用选定的线帽类型来绘制。

Linedash pattern(虚线模式)允许我们沿着描边绘制虚线。我们通过在CGContextSetLineDash结构体中指定虚线数组和虚线相位来控制虚线的大小及位置。

void CGContextSetLineDash (
                           CGContextRef ctx,
                           CGFloat phase,
                           const CGFloat lengths[],
                           size_t count
                           );

其中lengths属性是一个CGFloat型数组,每个CGFloat值控制点线的实现长度和间距.比如{2,3}代表实线长度为2,间距为3.其实也可以理解实现和没有的概念,反复重复你设置的值,该值是在绘制线段与未绘制线段之间交替。phase属性指定虚线模式的起始点。图3-11显示了虚线模式:

Figure 3-11  Examples
of line dash patterns

描边颜色空间(stroke color space)定义了Quartz如何解析描边的颜色。我们同样也可以指定一个封装了颜色和颜色空间的CGColorRef数据类型。

Functions for Stroking a Path

Quartz提供了表3-4中的函数来描边当前路径。其中一些是描边矩形及椭圆的便捷函数。

Table 3-4  Functions that stroke paths

Function


Description


CGContextStrokePath


Strokes the current path.


CGContextStrokeRect


Strokes the specified rectangle.


CGContextStrokeRectWithWidth


Strokes the specified rectangle, using the specified line width.


CGContextStrokeEllipseInRect


Strokes an ellipse that fits inside the specified rectangle.


CGContextStrokeLineSegments


Strokes a sequence of lines.


CGContextDrawPath


If you pass the constant kCGPathStroke, strokes the current path. See Filling
a Path
 if you want to both fill and stroke a path.

函数CGContextStrokeLineSegments功能等同于如下代码:

CGContextBeginPath (context);
for (k = 0; k < count; k += 2) {
    CGContextMoveToPoint(context, s[k].x, s[k].y);
    CGContextAddLineToPoint(context, s[k+1].x, s[k+1].y);
}
CGContextStrokePath(context);

当我们调用CGContextStrokeLineSegments时,我们通过点数组来指定线段,并组织成点对的形式。每一对是由线段的起始点与终止点组成。例如,数组的第一个点指定了第一条直线的起始点,第二个点是第一条直线的终点,第三个点是第二条直线的起始点,依此类推。

Filling a Path

当我们填充当前路径时,Quartz将路径包含的每个子路径都看作是闭合的。然后,使用这些闭合路径并计算填充的像素。
Quartz有两种方式来计算填充区域。椭圆和矩形这样的路径其区域都很明显。但是如果路径是由几个重叠的部分组成或者路径包含多个子路径(如图3-12所示),我们则有两种规则来定义填充区域。

默认的规则是非零缠绕数规则(nonzero windingnumber rule)。为了确定一个点是否需要绘制,我们从该点开始绘制一条直线穿过绘图的边界。从0开始计数,每次路径片断从左到右穿过直线,计数加1;而从右到左穿过直线时,计数减1。如果结果为0,则不绘制该点,否则绘制。路径片断绘制的方向会影响到结果。图3-13显示了使用非缠绕数规则对内圆和外圆进行填充的结果。当两个圆绘制方向相同时,两个圆都被填充。如果方向相反,则内圆不填充。

我们也可以使用偶数-奇数规则来确定一个点是否应该被绘制,我们从该点开始绘制一条直线穿过绘图的边界。计算穿过该直线的路径片断的数目。如果是奇数,则绘制该点,如果是偶数,则不绘制该点。路径片断绘制的方向不影响结果。如图3-12所示,无论两个圆的绘制方向是什么,填充结果都是一样的。

Figure 3-12  Concentric
circles filled using different fill rules

Quartz提供了表3-5中的函数来填充当前路径。其中一些是填充矩形及椭圆的便捷函数。

Table 3-5  Functions that fill paths

Function


Description


CGContextEOFillPath


Fills the current path using the even-odd rule.


CGContextFillPath


Fills the current path using the nonzero winding number rule.


CGContextFillRect


Fills the area that fits inside the specified rectangle.


CGContextFillRects


Fills the areas that fits inside the specified rectangles.


CGContextFillEllipseInRect


Fills an ellipse that fits inside the specified rectangle.


CGContextDrawPath


Fills the current path if you pass kCGPathFill (nonzero winding number rule) or kCGPathEOFill (even-odd
rule). Fills and strokes the current path if you pass kCGPathFillStroke or kCGPathEOFillStroke.

Setting Blend Modes

混合模式指定了Quartz如何将绘图绘制到背景上。Quartz默认使用普通混合模式(normal
blend mode),该模式使用如下公式来计算前景绘图与背景绘图如何混合:

result = (alpha * foreground) + (1 - alpha) *background

Color
and Color Spaces
章节里面详细讨论了颜色值的alpha组件,该组件用于指定颜色的透明度。在本章的例子中,我们可以假设颜色值是完全不透明的(alpha
= 1.0)。对于不透明的颜色值,当我们用普通混合模式时,所有绘制于背景之上的绘图都会遮掩住背景。

我们可以调用函数CGContextSetBlendMode,并传递适当的混合模式常量值来设置混合模式来达到我们想到的效果。记住混合模式是图形状态的一部分。如果调用了函数CGContextSaveGState 来改变混合模式,则调用函数 CGContextRestoreGState来重新设置混合模式为普通混合模式。

接下来的内容例举了不同混合模式上将图3-13的矩形绘制到图3-14的矩形之上的效果。背景图使用普通混合模式来绘制。然后调用CGContextSetBlendMode函数来改变混合模式。最后绘制前景矩形

Figure 3-13  The
rectangles painted in the foreground

Figure 3-14  The
rectangles painted in the background

注意:我们同样可以使用混合模式来组合两张图片或将图片与图形上下文中已有的内容进行混合。Using
Blend Modes with Images
提供了相关信息对于如何处理使用混合模式来组合两张图片。

Normal Blend Mode

由于普通混合模式是默认的混合模式,所以在设置了其它混合模式后,可以调用CGContextSetBlendMode并传递kCGBlendModeNormal来将混合模式重设为默认。图3-15显示了普通混合模式上图3-13与图3-14混合的效果。

Figure 3-15  Rectangles
painted using normal blend mode

Multiply Blend Mode

正片叠底混合模式指定将前景的图片采样与背景图片采样相乘。结果颜色至少与两个采样颜色之一一样暗。图3-16显示了混合结果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeMultiply来设置这种混合模式。

Figure 3-16  Rectangles
painted using multiply blend mode

Screen Blend Mode

屏幕混合模式指定将前景图片采样的反转色与背景图片的反转色相乘。结果颜色至少与两种采样颜色之一一样亮。图3-17显示了混合结果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeScreen来设置这种混合模式。

Figure
3-17  Rectangles painted using screen blend mode

Overlay Blend Mode

      叠加混合模式是将前景图片与背景图片或者正片叠底,或者屏幕化,这取决于背景颜色。背景颜色值与前景颜色值以反映出背景颜色的亮度与暗度。图3-18显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeOverlay来设置这种混合模式。

Figure 3-18  Rectangles
painted using overlay blend mode

Darken Blend Mode

通过选择前景图片与背景图片更暗的采样来混合图片采样。背景图片采样被前景图片采样更暗的部分取代,而其它部分不变。图3-19显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeDarken来设置这种混合模式。

Figure 3-19  Rectangles
painted using darken blend mode

Lighten Blend Mode

通过选择前景图片与背景图片更亮的采样来混合图片采样。背景图片采样被前景图片采样更亮的部分取代,而其它部分不变。图3-20显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeLighten来设置这种混合模式。

Figure 3-20  Rectangles
painted using lighten blend mode

Color Dodge Blend Mode

加亮背景图片采样以反映出前景图片采样。被指定为黑色的前景图片采样值将不产生变化。图3-21显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeColorDodge来设置这种混合模式。

Figure 3-21  Rectangles
painted using color dodge blend mode

Color Burn Blend Mode

加深背景图片采样以反映出前景图片采样。被指定为白色的前景图片采样值将不产生变化。图3-21显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeColorBurn来设置这种混合模式。

Figure 3-22  Rectangles
painted using color burn blend mode

Soft Light Blend Mode

根据前景采样颜色减淡或加深颜色值。如果前景采样颜色比50%灰度值更亮,则减淡背景,类似于Dodge模式。如果前景采样颜色比50%灰度值更暗,则加强背景,类似于Burn模式。纯黑或纯白的图片采样将产生更暗或更亮的区域。但是但是不产生纯白或纯黑的颜色。该效果类似于将一个漫射光源放于一个前景图前。该效果用于在场景中添加高光效果。图3-23显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeSoftLight来设置这种混合模式。

Figure 3-23  Rectangles
painted using soft light blend mode

Hard Light Blend Mode

根据前景图片采样颜色正片叠加或屏幕化颜色。如果前景采样颜色比50%灰度值更亮,则减淡背景,类似于screen模式。如果前景采样颜色比50%灰度值更暗,则加深背景,类似于multiply模式。如果前景采样颜色等于50%灰度,则前景颜色不变。纯黑与纯白的颜色图片采样将产生纯黑或纯白的颜色值。该效果类似于将一个强光源放于一个前景图前。该效果用于在场景中添加高光效果。图3-24显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeHardLight来设置这种混合模式。

Figure 3-24  Rectangles
painted using hard light blend mode

Difference Blend Mode

将前景图片采样颜色值与背景图片采样值相减,相减的前后关系取决于哪个采样的亮度值更大。黑色的前景采样值不发生变化;白色值转化为背景的值。图3-25显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeDifference来设置这种混合模式。

Figure 3-25  Rectangles
painted using difference blend mode

Exclusion Blend Mode

该效果类似于Difference效果,只是对比度更低。黑色的前景采样值不发生变化;白色值转化为背景的值。图3-26显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeExclusion来设置这种混合模式。

Figure 3-26  Rectangles
painted using exclusion blend mode

Hue Blend Mode

使用背景的亮度和饱和度与前景的色相混合。图3-27显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeHue来设置这种混合模式。

Figure 3-27  Rectangles
painted using hue blend mode

Saturation Blend Mode

混合背景的亮度和色相前景的饱和度。背景中没有饱和度的区域不发生变化。图3-28显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeSaturation来设置这种混合模式。

Figure 3-28  Rectangles
painted using saturation blend mode

Color Blend Mode

混合背景的亮度值与前景的色相与饱和度。该模式保留图片的灰度级。我们可以使用该模式绘制单色图片或彩色图片。图3-29显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeColor来设置这种混合模式。

Figure 3-29  Rectangles
painted using color blend mode

Luminosity Blend Mode

将背景图片的色相、饱和度与背景图片的亮度相混合。该模块产生一个与Color Blend模式相反的效果。图3-30显示了混合效果。我们可以调用CGContextSetBlendMode并传递kCGBlendModeLuminosity来设置这种混合模式。

Figure 3-30  Rectangles
painted using luminosity blend mode

Clipping to a Path

当前裁剪区域是从路径中创建,作为一个遮罩,从而允许遮住我们不想绘制的部分。例如,我们有一个很大的位图图片,但只需要显示其中一小部分,则可以设置裁减区域来显示我们想显示的部分。

当我们绘制的时候,Quartz只渲染裁剪区域里面的东西。裁剪区域内的闭合路径是可见的;而在区域外的部分是不可见的。

当图形上下文初始创建时,裁减区域包含上下文所有的可绘制区域(例如,PDF上下文的media
box)。我们可以通过设置当前路径来改变裁剪区域,然后使用裁减函数来取代绘制函数。裁剪函数与当前已有的裁剪区域求交集以获得路径的填充区域。因此,我们可以求交取得裁减区域,缩小图片的可视区域,但是不能扩展裁减区域。

裁减区域是图形状态的一部分。为了恢复先前的裁减区域,我们可以在裁减前保存图形状态,并在裁减绘制后恢复图 形状态。

代码清单3-1显示了绘制圆形后设置裁减区域。该段代码使得绘图被裁减,效果类似于图3-3所示。对其它的例子可以看see Clip
the Context
 in the chapter Gradients

Listing
3-1 
Setting up a circular clip area

CGContextBeginPath (context);
CGContextAddArc (context, w/2, h/2, ((w>h) ? h : w)/2,0,2*PI,0);
CGContextClosePath (context);
CGContextClip (context);
 Table 3-6  Functions that clip the graphics context

Function


Description


CGContextClip


Uses the nonzero winding number rule to calculate the intersection of the current path with the current clipping path.


CGContextEOClip


Uses the even-odd rule to calculate the intersection of the current path with the current clipping path.


CGContextClipToRect


Sets the clipping area to the area that intersects both the current clipping path and the specified rectangle.


CGContextClipToRects


Sets the clipping area to the area that intersects both the current clipping path and region within the specified rectangles.


CGContextClipToMask


Maps a mask into the specified rectangle and intersects it with the current clipping area of the graphics context. Any subsequent path drawing you perform to the graphics context is clipped. (See Masking
an Image by Clipping the Context
.)

时间: 2024-08-02 17:16:07

Quartz 2D编程指南(3)路径(Paths)的相关文章

Quartz 2D编程指南(1) - 概览

Quartz 2D编程指南是论坛会员德鲁伊翻译的国外的Quartz 2D一系列学习资料,供大家参考 Quartz 2D是一个二维图形绘制引擎,支持iOS环境和Mac OS X环境.我们可以使用Quartz 2D API来实现许多功能,如基本路径的绘制.透明度.描影.绘制阴影.透明层.颜色管理.反锯齿.PDF文档生成和PDF元数据访问.在需要的时候,Quartz 2D还可以借助图形硬件的功能.在Mac OS X中,Quartz 2D可以与其它图形图像技术混合使用,如Core Image.Core

Quartz 2D编程指南(2) - 图形上下文

一个Graphics Context表示一个绘制目标.它包含绘制系统用于完成绘制指令的绘制参数和设备相关信息.Graphics Context定义了基本的绘制属性,如颜色.裁减区域.线条宽度和样式信息.字体信息.混合模式等. 我们可以通过几种方式来获取Graphics Context:Quartz提供的创建函数.Mac OS X框架或IOS的UIKit框架提供的函数.Quartz提供了多种Graphics Context的创建函数,包括bitmap和PDF,我们可以使用这些Graphics Co

Quartz 2D编程指南(7) - 阴影(Shadows)

阴影是绘制在一个图形对象下的且有一定偏移的图片,它用于模拟光源照射到图形对象上所形成的阴影效果,如果7-1所示.文本也可以有阴影.阴影可以让一幅图像看上去是立体的或者是浮动的. 阴影有三个属性: 1.x偏移值,用于指定阴影相对于图片在水平方向上的偏移值. 2.y偏移值,用于指定阴影相对于图片在竖直方向上的偏移值. 3.模糊(blur)值,用于指定图像是有一个硬边(hard edge,如图7-2左边图片所示),还是一个漫射边(diffuse edge,如图7-1右边图片所示) 本章将描述阴影是如何

Quartz 2D编程指南(4) - 颜色和颜色空间

不同的设备(显示器.打印机.扫描仪.摄像头)处理颜色的方式是不同的.每种设备都有其所能支持的颜色值范围.一种设备能支持的颜色可能在其它设备中无法支持.为了有效的使用颜色及理解Quartz 2D中用于颜色及颜色空间的函数,我们需要熟悉在Color Management Overview文档中所使用的术语.该文档中讨论了色觉.颜色值.设备依赖及设备颜色空间.颜色匹配问题.再现意图(rendering intent).颜色管理模块和ColorSync.在本章中,我们将学习Quartz处理颜色和颜色空间

Quartz 2D编程指南(5)变换(Transforms)

Quartz2D绘制模型定义了两种完全独立的坐标空间:用户空间(用于表现文档页)和设备空间(用于表现设备的原生分辨率).用户坐标空间用浮点数表示坐标,与设备空间的像素分辨率没有关系.当我们想要打印和显示文档时, Quartz会将用户空间坐标系统映射到设备空间坐标系统.因此,我们不需要重写应用程序或添加额外的代码来调整应用程序的输出以适应不同的设备. 我们可以通过操作CTM(current transformation matrix当前变换矩阵)来修改默认的用户空间.在创建图形上下文后,CTM是单

Quartz 2D编程指南- PDF文档的创建、显示及转换

PDF文档存储依赖于分辨率的向量图形.文本和位图,并用于程序的一系列指令中.一个PDF文档可以包含多页的图形和文本.PDF可用于创建跨平台.只读的文档,也可用于绘制依赖于分辨率的图形.         Quartz为所有应用程序创建高保真的PDF文档,这些文档保留应用的绘制操作,如图13-1所示.PDF文档的结果将通过系统的其它部分或第三方法的产品来有针对性地进行优化.Quartz创建的PDF文档在Preview和Acrobat中都能正确的显示. Quartz不仅仅只使用PDF作为它的数字页,它

Quartz 2D Programming Guide

Quartz 2D Programming  Guide 官方文档: Quartz 2D Programming Guide 译文: Quartz 2D编程指南(1) - 概览 Quartz 2D编程指南(2) - 图形上下文(Graphics Contexts) Quartz 2D编程指南(3) - 路径(Paths)[上] Quartz 2D编程指南(3) - 路径(Paths)[下] Quartz 2D编程指南(4) - 颜色和颜色空间 Quartz 2D编程指南(5) - 变换 Quar

Quartz2D 编程指南(一)概览、图形上下文、路径、颜色与颜色空间

概览 图形上下文 路径 颜色与颜色空间 变换 图案 阴影 渐变 透明层 Quartz 2D 中的数据管理 位图与图像遮罩 CoreGraphics 绘制 Layer 0.说明 本篇博客主要是对官方文档的总结与补充.翻译部分参考了南峰子的博客.你可以在参考资料中查看. 1.概览 简介 Quartz2D 是二维图形绘制引擎,支持 iOS 和 OS X. Page Quartz2D 在图像中使用了绘画者模型.在绘画者模型中,每个连续的绘制操作都是将一个绘制层放置于一个画布,我们通常称这个画布为 Pag

iOS开发——图形编程OC篇&amp;(六)Quartz 2D高级使用(二)

Quartz 2D高级使用 一.绘图路径 A.简单说明 在画线的时候,方法的内部默认创建一个path.它把路径都放到了path里面去. 1.创建路径  cgmutablepathref 调用该方法相当于创建了一个路径,这个路径用来保存绘图信息. 2.把绘图信息添加到路径里边. 以前的方法是点的位置添加到ctx(图形上下文信息)中,ctx 默认会在内部创建一个path用来保存绘图信息. 在图形上下文中有一块存储空间专门用来存储绘图信息,其实这块空间就是CGMutablePathRef. 3.把路径