Status SetFillMode(FillMode fillmode); FillMode GetFillMode(VOID);
关于画路径轮廓和填充路径的例子,前面已经有了很多,这里就不再列举了。
6.获取点信息
在创建路径并添加各种几何图形或字符串之后,我们可以调用如下一些GraphicsPath类的方法,来获取路径中点的信息。包括点的坐标信息和点的类型信息:
INT GetPointCount(VOID); // 获取路径中的总点数
Status GetPathPoints(Point *points, INT count); // 获取路径中(指定数目的)整数点数组 Status GetPathPoints(PointF *points, INT count); // 获取路径中(指定数目的)浮点数点数组 Status GetPathTypes(BYTE *types, INT count); // 获取路径中(指定数目的)点类型数组 例如:
GraphicsPath path; …… // 添加若干图形到路径
int n = path.GetPointCount(); Point *points = new Point[n]; path.GetPathPoints(points, n);
graph.DrawLines(&Pen(Color::Green), points, n); DrawPoints(graph, Color::Red, 4, points, n);
13.1.2 路径渐变刷
路径可以表示复杂的图形,可以用于绘制这些图形的轮廓和填充,也可以用于创建区域(在下一节介绍)和颜色渐变刷。后者在前面美术字部分的彩心字符串例中(参见12.8.3的5.),我们已经用过。
与其它具体刷(如实心刷、条纹刷和纹理刷等)类一样,路径渐变(梯度)刷类PathGradientBrush,也是Brush类的派生类。它有3个构造函数:
PathGradientBrush(const GraphicsPath *path); PathGradientBrush(const Point *points, INT count,
WrapMode wrapMode = WrapModeClamp);
6
PathGradientBrush(const PointF *points, INT count,
WrapMode wrapMode = WrapModeClamp);
第一个构造函数从现有路径对象来创建画刷,后两个则是从整数或浮点数点集来直接创建画刷,而且它们两个还有一个指定重复排列的输入参数wrapMode,默认值为WrapModeClamp(不重复排列)。
路径刷的颜色,一般是从路径点(周边轮廓)向路径中心渐变。路径刷的默认中心为路径的形心,可以用路径刷方法SetCenterPoint来重新设置:
Status SetCenterPoint(const Point &point); Status SetCenterPoint(const PointF &point);
其中的中心点,可以位于任何位置,包括在路径的范围之外。对应的获取刷中心的方法是:
Status GetCenterPoint(Point *point); Status GetCenterPoint(PointF *point); 其它常用的路径刷方法有:
Status SetCenterColor(const Color &color); // 设置刷中心颜色
Status SetSurroundColors(const Color *colors, INT *count); // 设置路径点颜色 Status GetCenterColor(Color *color); // 获取刷中心颜色 INT GetSurroundColorCount(VOID); // 获取路径点颜色数目
Status GetSurroundColors(Color *colors, INT *count); // 获取路径点颜色数组
其中,路径刷的中心色和路径点色,默认都为背景色(白色)。
例如(用路径刷画五角星,参见图13-3):
INT count = 10;
Point points[] = {Point(100, 0), Point(122, 69),
Point(195, 69), Point(137, 111), Point(159, 181), Point(100, 138), Point(41, 181), Point(63, 111), Point(5, 69), Point(78, 69)};
GraphicsPath path;
path.AddPolygon(points, count); Graphics graph(pDC->m_hDC); PathGradientBrush pgBrush(&path);
pgBrush.SetCenterColor(Color::Red/*Green*/);
7
graph.FillPath(&pgBrush, &path);
Color cols[] = {Color::Black, Color::Green, Color::Blue,
Color::White, Color::Black, Color::Green, Color::Blue, Color::White, Color::Black, Color::Green};
/*Color cols[] = {Color::Cyan, Color::Aqua, Color::Blue,
Color::Chartreuse, Color::Coral, Color::CadetBlue, Color::HotPink, Color::Turquoise, Color::LightSkyBlue, Color::DeepPink};
pgBrush.SetCenterColor(Color::White);*/ pgBrush.SetSurroundColors(cols, &count); graph.TranslateTransform(200.0f, 0); graph.FillPath(&pgBrush, &path); for (int i = 0; i < count; i++)
cols[i] = Color(rand() % 255, rand() % 255, rand() % 255);
pgBrush.SetSurroundColors(cols, &count);
pgBrush.SetCenterColor(Color(rand() % 255, rand() % 255,
rand() % 255));
graph.TranslateTransform(-200.0f, 200.0f); graph.FillPath(&pgBrush, &path); for (int i = 0; i < count; i++)
cols[i] = Color(rand() % 255, rand() % 255, rand() % 255);
pgBrush.SetSurroundColors(cols, &count);
pgBrush.SetCenterColor(Color(rand() % 255, rand() % 255,
rand() % 255));
graph.TranslateTransform(200.0f, 0.0f); graph.FillPath(&pgBrush, &path);
输出结果见图13-3(由于下排的两个五角星,使用的是随机色,所以每次刷新时,颜色都不一样)。
如果将边点全改成红色、绿色或蓝色,中心改为白色,则输出效果如图13-4所示。 又例如(用路径刷画平铺六边形,参见图13-5和图13-6):
8
a)
b)
图13-3 路径刷五角星
a)上排左为红心和白边点,上排右为红心和和黑、绿、蓝、白边点
b) 上排的左右皆为绿心,边点色同a)的
a)和b)下排的中心点和边点都为随机色,刷新后颜色会变
图13-4 路径刷五角星(白心,红、绿、蓝边)
#include
void FillHexagon(HDC hdc, RectF &rect) // 用路径刷画平铺六边形 {
float radian = 3.1415926f / 180.0f;
float l = 50.0f, fh = l * sin(60.0f * radian); PointF pts[] = {PointF(50.0f, 0.0f),
PointF(50.0f * 1.5f, 0.0f), PointF(50.0f, 0.0f), PointF(50.0f / 2.0f, -fh), PointF(-50.0f / 2.0f, -fh), PointF(-50.0f, 0.0f), PointF(-50.0f * 1.5f, 0.0f), PointF(-50.0f, 0.0f), PointF(-50.0f / 2.0f, fh), PointF(50.0f / 2.0f, fh)};
PathGradientBrush pgBrush(pts, 10);
9
}
pgBrush.SetWrapMode(WrapModeTile); Graphics graph(hdc);
pgBrush.SetCenterColor(Color::Red); graph.FillRectangle(&pgBrush, rect); graph.TranslateTransform(75.0f, fh);
图13-5 六边形坐标
pgBrush.SetCenterColor(Color::Green);
graph.FillRectangle(&pgBrush, -75.0f, -fh, rect.Width,
rect.Height);
void CGdipDrawView::OnDraw(CDC* pDC) { }
……
RECT srect;
GetClientRect(&srect);
RectF rect(0.0f, 0.0f, REAL(srect.right),
REAL(srect.bottom));
FillHexagon(pDC->m_hDC, rect); // 用路径刷画平铺六边形
图13-6 路径刷平铺六边形
10