版本记录
版本号 | 时间 |
---|---|
V1.0 | 2018.09.04 |
前言
Quartz 2D
框架相信大家都知道,也都一直在使用。Quartz 2D
的API是纯C语言的,它是一个二维绘图引擎,同时支持iOS和Mac系统。Quartz 2D
的API来自于Core Graphics
框架,数据类型和函数基本都以CG作为前缀,接下来几篇我们就一起来看一下这个框架。感兴趣可以看上面几篇文章。
1. Quartz 2D编程指南 (一) —— 简介(一)
2. Quartz 2D编程指南 (二) —— Quartz 2D概览(二)
3. Quartz 2D编程指南 (三) —— 图形上下文(三)
4. Quartz 2D编程指南 (四) —— Paths路径(一)
Painting a Path - 绘制路径
您可以通过描边或填充或两者都参与来绘制当前路径。 描边画一条跨越路径的线。 填充绘制路径中包含的区域。 Quartz具有允许您描边路径,填充路径或者描边和填充路径的功能。 描边线(宽度,颜色等)的特征,填充颜色以及Quartz用于计算填充区域的方法都是图形状态的一部分(参见 Graphics States)。
1. Parameters That Affect Stroking - 影响描边的参数
您可以通过修改表3-1中列出的参数来影响路径的描边方式。 这些参数是图形状态的一部分,这意味着您为参数设置的值会影响所有后续描边,直到您将参数设置为另一个值。
Table 3-1 Parameters that affect how Quartz strokes the current path
line width
是线的总宽度,以用户空间为单位表示。 该线横跨路径,两侧总宽度的一半。
line join
指定Quartz如何绘制连接线段之间的连接。 Quartz支持表3-2中描述的线连接样式。 默认样式是斜接连接miter join
。
Table 3-2 Line join styles
line cap
指定CGContextStrokePath
用于绘制线的端点的方法。 Quartz支持表3-3中描述的线帽样式。 默认样式是对接上限butt cap
。
Table 3-3 Line cap styles
封闭的子路径将起点视为连接线段之间的连接点;使用选定的line-join
方法呈现起点。 相反,如果通过添加连接到起点的线段来关闭路径,则使用选定的线帽方法绘制路径的两端。
line dash pattern
- 线条虚线图案允许您沿着描边路径绘制分段线。 您可以通过将破折号数组和破折号阶段指定为CGContextSetLineDash
的参数来控制破折号线段的大小和位置:
void CGContextSetLineDash (
CGContextRef ctx,
CGFloat phase,
const CGFloat lengths[],
size_t count
);
长度lengths
参数的元素指定短划线的宽度,在线的绘制和未绘制段之间交替。 phase
参数指定破折号模式的起始点。 图3-11显示了一些线划线图案。
描边颜色空间color space
决定了Quartz如何解释描边颜色空间。 您还可以指定封装颜色和颜色空间的Quartz颜色(CGColorRef
数据类型)。 有关设置颜色空间和颜色的详细信息,请参阅Color and Color Spaces。
2. Functions for Stroking a Path - 描边路径的函数
Quartz提供表3-4中所示的功能,用于描边当前路径。 一些是用于描边矩形或椭圆的便利函数。
Table 3-4 Functions that stroke paths
函数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
时,您将线段指定为点数组,按对进行组织。 每对由线段的起点和线段的终点组成。 例如,数组中的第一个点指定第一行的起始位置,第二个点指定第一行的结束位置,第三个点指定第二行的起始位置,依此类推。
3. Filling a Path - 填充路径
填充当前路径时,Quartz
就像关闭路径中包含的每个子路径一样。然后它使用这些封闭的子路径并计算要填充的像素。 Quartz可以通过两种方式计算填充区域。椭圆形和矩形等简单路径具有明确的区域。但是,如果路径由重叠的段组成,或者路径包含多个子路径,例如图3-12中所示的同心圆,则可以使用两个规则来确定填充区域。
默认填充规则称为非零绕组编号规则- nonzero winding number rule
。要确定是否应绘制特定点,请从该点开始并绘制超出图形边界的线。从计数0开始,每次路径段从左到右穿过该行时,向计数加1,并且每当路径段从右到左穿过该行时,减去1。如果结果为0,则不绘制该点。否则,该点被绘制。绘制路径段的方向会影响结果。图3-12显示了使用非零绕组编号规则填充的两组内圆和外圆。当每个圆圈以相同方向绘制时,两个圆圈都被填充。当圆圈以相反方向绘制时,内圆圈未被填充。
您可以选择使用偶数规则 - even-odd rule
。要确定是否应绘制特定点,请从该点开始并绘制超出图形边界的线。计算线穿过的路径段的数量。如果结果是奇数,则绘制该点。如果结果是偶数,则不绘制点。绘制路径段的方向不会影响结果。如图3-12所示,每个圆的绘制方向无关紧要,填充将始终如图所示。
Quartz提供表3-5中所示的函数,用于填充当前路径。 一些是用于描边矩形或椭圆的便利函数。
Table 3-5 Functions that fill paths
4. Setting Blend Modes - 设置混合模式
混合模式(Blend modes)
指定Quartz如何在背景上进行绘制。 Quartz默认使用普通混合模式,它使用以下公式将前景绘画与背景绘画相结合:
result =(alpha * foreground)+(1 - alpha)* background
Color and Color Spaces提供了颜色的alpha分量的详细讨论,它指定颜色的不透明度。对于本节中的示例,您可以假设颜色完全不透明(alpha值= 1.0)。对于不透明的颜色,当您使用普通混合模式进行绘制时,在背景上绘制的任何内容都会完全遮盖背景。
您可以通过调用函数CGContextSetBlendMode
设置混合模式以实现各种效果,并传递适当的混合模式常量。请记住,混合模式是图形状态的一部分。如果在更改混合模式之前使用CGContextSaveGState
函数,则调用函数CGContextRestoreGState
会将混合模式重置为normal
。
本节的其余部分显示了在图3-14中所示的矩形上绘制图3-13中所示矩形的结果。在每种情况下(图3-15至图3-30),使用普通混合模式绘制背景矩形。然后通过使用适当的常量调用函数CGContextSetBlendMode
来更改混合模式。最后,绘制前景矩形。
注意:您还可以使用混合模式合成两个图像,或者将图像合成到已经绘制到图形上下文的任何内容上。 Using Blend Modes with Images可提供有关如何使用混合模式合成图像的信息,并显示将混合模式应用于两个图像的结果。
(1)Normal Blend Mode - 正常混合模式
由于普通混合模式是默认的混合模式,因此只使用常量kCGBlendModeNormal
调用函数CGContextSetBlendMode
,以便在使用其他混合模式常量之一后将混合模式重置为默认值。 图3-15显示了使用普通混合模式绘制图3-14上绘制图3-13的结果。
(2)Multiply Blend Mode - 乘法混合模式
乘法混合模式指定将前景图像样本与背景图像样本相乘。 得到的颜色至少与两种样本颜色中的任何一种颜色一样深。 图3-16显示了使用乘法混合模式绘制图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeMultiply
调用函数CGContextSetBlendMode
。
(3) Screen Blend Mode - 屏幕混合模式
屏幕混合模式指定将前景图像样本的倒数与背景图像样本的倒数相乘。 得到的颜色至少与两种样本颜色中的任何一种颜色一样浅。 图3-17显示了使用屏幕混合模式绘制图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeScreen
调用函数CGContextSetBlendMode
。
(4) Overlay Blend Mode - 叠加混合模式
叠加混合模式指定将前景图像样本与背景图像样本相乘,具体取决于背景颜色。 背景颜色与前景色混合以反映背景的亮度或暗度。 图3-18显示了使用叠加混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeOverlay
调用函数CGContextSetBlendMode
。
(5) Darken Blend Mode - 变暗混合模式
指定通过选择较暗的样本(来自前景图像或背景)来创建合成图像样本。 背景图像样本被任何较暗的前景图像样本替换。 否则,背景图像样本保持不变。 图3-19显示了使用变暗混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeDarken
调用函数CGContextSetBlendMode
。
(6) Lighten Blend Mode - 减轻混合模式
指定通过选择较亮的样本(来自前景或背景)来创建合成图像样本。 结果是背景图像样本被任何较轻的前景图像样本替换。 否则,背景图像样本保持不变。 图3-20显示了使用淡化混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeLighten
调用函数CGContextSetBlendMode
。
(7) Color Dodge Blend Mode - 颜色减淡混合模式
指定使背景图像样本变亮以反映前景图像样本。 指定黑色的前景图像样本值不会产生更改。 图3-21显示了使用颜色减淡混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeColorDodge
调用函数CGContextSetBlendMode
。
(8) Color Burn Blend Mode - 彩色混合模式
指定使背景图像样本变暗以反映前景图像样本。 指定白色的前景图像样本值不会产生更改。 图3-22显示了使用彩色混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeColorBurn
调用函数CGContextSetBlendMode
。
(9) Soft Light Blend Mode - 柔光混合模式
指定使颜色变暗或变亮,具体取决于前景图像样本颜色。 如果前景图像样本颜色浅于50%灰色,则背景会变亮,类似于dodging
。 如果前景图像样本颜色深于50%灰色,则背景变暗,类似于burning
。 如果前景图像样本颜色等于50%灰色,则不更改背景。 等于纯黑色或纯白色的图像样本会产生较暗或较亮的区域,但不会产生纯黑色或白色。 整体效果类似于通过在前景图像上照射漫反射聚光灯所实现的效果。 使用此选项可为场景添加高光。 图3-23显示了使用柔和光混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeSoftLight
调用函数CGContextSetBlendMode
。
(10) Hard Light Blend Mode - 硬光混合模式
指定乘法或screen
颜色,具体取决于前景图像样本颜色。 如果前景图像样本颜色浅于50%灰色,则背景会变亮,类似于screening
。 如果前景图像样本颜色深于50%灰色,则背景变暗,类似于相乘。 如果前景图像样本颜色等于50%灰度,则不更改前景图像。 等于纯黑色或纯白色的图像样本产生纯黑色或白色。 整体效果类似于通过在前景图像上发出刺眼的聚光灯而实现的效果。 使用此选项可为场景添加高光。 图3-24显示了使用硬光混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeHardLight
调用函数CGContextSetBlendMode
。
(11) Difference Blend Mode - 差异混合模式
指定从背景图像样本颜色中减去前景图像样本颜色,或reverse
,根据哪个样本具有更高的亮度值。 黑色的前景图像样本值不会产生任何变化; 白色反转背景颜色值。 图3-25显示了使用差异混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeDifference
调用函数CGContextSetBlendMode
。
(12) Exclusion Blend Mode - 排除混合模式
指定与kCGBlendModeDifference
生成的效果类似的效果,但对比度较低。 黑色的前景图像样本值不会产生变化; 白色反转背景颜色值。 图3-26显示了使用排除混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeExclusion
调用函数CGContextSetBlendMode
。
(13) Hue Blend Mode - 色调混合模式
指定使用背景的亮度和饱和度值以及前景图像的色调。 图3-27显示了使用色调混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeHue
调用函数CGContextSetBlendMode
。
(14) Saturation Blend Mode - 饱和度混合模式
指定使用背景的亮度和色调值以及前景图像的饱和度。 没有饱和的背景区域(即纯灰色区域)不会产生变化。 图3-28显示了使用饱和度混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeSaturation
调用函数CGContextSetBlendMode
。
(15) Color Blend Mode - 颜色混合模式
指定使用背景的亮度值以及前景图像的色调和饱和度值。 此模式保留图像中的灰度级。 您可以使用此模式为单色图像着色或着色彩色图像。 图3-29显示了使用颜色混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeColor
调用函数CGContextSetBlendMode
。
(16) Luminosity Blend Mode - 亮度混合模式
指定使用背景的色调和饱和度以及前景图像的亮度。 此模式创建的效果与kCGBlendModeColor
创建的效果相反。 图3-30显示了使用光度混合模式在图3-14上绘制图3-13的结果。 要使用此混合模式,请使用常量kCGBlendModeLuminosity
调用函数CGContextSetBlendMode
。
Clipping to a Path - 剪切路径
当前剪切区域(current clipping area )
是从用作蒙版的路径创建的,允许您阻止不想绘制的页面部分。例如,如果您有一个非常大的位图图像并且只想显示它的一小部分,则可以将剪切区域设置为仅显示您要显示的部分。
绘制时,Quartz仅在剪切区域内渲染绘制。在剪切区域的封闭子路径内发生的绘图是可见的;在剪切区域的闭合子路径之外发生的绘制不是。
最初创建图形上下文时,剪切区域包括上下文的所有可绘制区域(例如,PDF上下文的媒体框)。您可以通过设置当前路径然后使用剪切功能而不是绘图功能来更改剪切区域。剪切功能将当前路径的填充区域与现有剪切区域相交。因此,您可以与剪切区域相交,缩小图片的可见区域,但不能增加剪裁区域的面积。
剪切区域是图形状态的一部分。要将剪切区域恢复到先前的状态,可以在剪切之前保存图形状态,并在完成剪切绘图后恢复图形状态。
Listing 3-1
显示了一个代码片段,用于设置圆形的剪切区域。此代码会导致绘图被剪裁,类似于图3-3中所示。 (有关另一个示例,请参阅Gradients一章中的Clip the Context。)
// 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
后记
本篇主要讲述了Paths路径,感兴趣的给个赞或者关注~~~