📄 area.cpp
字号:
DeleteObject(hPen);
Label(hDC, P[0].x, P[0].y-20, "(Left, Top)");
Label(hDC, P[2].x-100, P[2].y+5, "(Bottom, Right)");
if ( i!=2 )
{
Label(hDC, S.x-40, S.y-20, "(xStart, yStart)");
Label(hDC, E.x-20, E.y-15, "(xEnd, yEnd)");
}
}
SelectObject(hDC, GetStockObject(WHITE_BRUSH));
DeleteObject(hBrush);
SetViewportOrgEx(hDC, 0, 0, NULL);
RestoreDC(hDC, nSave);
}
void DrawPieChart(HDC hDC, int x0, int y0, int x1, int y1,
double data[], COLORREF color[], int count)
{
double sum = 0;
for (int i=0; i<count; i++)
sum += data[i];
double angle = 0;
for (i=0; i<count; i++)
{
double a = data[i] * 2 * 3.14159265358 / sum;
HBRUSH hBrush = CreateSolidBrush(color[i]);
HGDIOBJ hOld = SelectObject(hDC, hBrush);
Pie(hDC, x0, y0, x1, y1,
(int) ((x1-x0) * cos(angle)),
- (int) ((y1-y0) * sin(angle)),
(int) ((x1-x0) * cos(angle+a)),
- (int) ((y1-y0) * sin(angle+a)));
angle += a;
SelectObject(hDC, hOld);
DeleteObject(hBrush);
}
}
void KMyCanvas::TestPieChart(HDC hDC)
{
// Pie Chart
double data[] = { 10, 20, 144, 50, 15 };
COLORREF color[] = { RGB(0xFF, 0, 0), RGB(0xFF, 0xFF, 0 ),
RGB(0xFF, 0, 0xFF), RGB(0, 0xFF, 0xFF),
RGB(0, 0xFF, 0) };
SetViewportOrgEx(hDC, 200, 150, NULL);
DrawPieChart(hDC, -100, -50, 100, 50, data, color, 5);
// Rounded Rectangle
SetViewportOrgEx(hDC, 450, 150, NULL);
for (int i=0; i<10; i++)
RoundRect(hDC, -100+i*10, -100+i*10, 100-i*10, 100-i*10, i*10, i*20);
//// RoundRect Definition ////////////////////////
SetViewportOrgEx(hDC, 300, 400, NULL);
const int A = 150;
const int B = 100;
POINT P[5] = { -A, -B, A, -B, A, B, -A, B, -A, -B };
int ew = A * 2/3;
int eh = B * 2/3;
// defining lines
{
LOGBRUSH logbrush = { BS_SOLID, RGB(0xFF, 0, 0), 0 };
KGDIObject brush(hDC, GetStockObject(HOLLOW_BRUSH));
KGDIObject attach(hDC, ExtCreatePen(PS_COSMETIC | PS_ALTERNATE, 1, & logbrush, 0, NULL));
// bounding rectangle, start/end lines
Rectangle(hDC, P[0].x, P[0].y, P[2].x, P[2].y);
// paint the area first, no pen
{
KGDIObject brush(hDC, CreateSolidBrush(RGB(0xFF, 0xFF, 0)));
KGDIObject pen (hDC, GetStockObject(NULL_PEN));
RoundRect(hDC, P[0].x, P[0].y, P[2].x, P[2].y, ew, eh);
}
// Four ellipse on corners
Ellipse(hDC, P[0].x, P[0].y, P[0].x+ew, P[0].y+eh);
Ellipse(hDC, P[0].x, P[2].y, P[0].x+ew, P[2].y-eh);
Ellipse(hDC, P[2].x, P[0].y, P[2].x-ew, P[0].y+eh);
Ellipse(hDC, P[2].x, P[2].y, P[2].x-ew, P[2].y-eh);
MoveToEx(hDC, P[0].x + ew-1, P[0].y-20, NULL);
LineTo(hDC, P[0].x + ew-1, P[0].y+eh/2);
Label(hDC, P[0].x + ew+2, P[0].y-20, "nLeft + nWidth");
MoveToEx(hDC, P[0].x + ew/2, P[0].y + eh-1, NULL);
LineTo(hDC, P[0].x - 20, P[0].y + eh-1);
Label(hDC, P[0].x - 120, P[0].y + eh, "nTop + nHeight");
}
// draw the outline, no brush
{
LOGBRUSH logbrush = { BS_SOLID, RGB(0, 0, 0xFF), 0 };
KGDIObject brush(hDC, GetStockObject(NULL_BRUSH));
KGDIObject attach(hDC, ExtCreatePen(PS_GEOMETRIC | PS_DOT, 5, & logbrush, 0, NULL));
RoundRect(hDC, P[0].x, P[0].y, P[2].x, P[2].y, ew, eh);
}
Label(hDC, P[0].x, P[0].y-20, "(nLeft, nTop)");
Label(hDC, P[2].x-100, P[2].y+5, "(nBottom, nRight)");
SetViewportOrgEx(hDC, 0, 0, NULL);
}
void KMyCanvas::TestPolyFillMode(HDC hDC)
{
int nSave = SaveDC(hDC);
LOGBRUSH logbrush = { BS_SOLID, RGB(0, 0, 0xFF), 0 };
KGDIObject brush(hDC, CreateSolidBrush(RGB(0xFF, 0xFF, 0)));
const POINT P2[] = { { 0, 0 }, { 0, 15 }, { 20, 15 } };
for (int i=0; i<2; i++)
{
SetViewportOrgEx(hDC, 50+350*i, 50, NULL);
{
KGDIObject pen(hDC, ExtCreatePen(PS_GEOMETRIC | PS_SOLID | PS_JOIN_MITER, 5, & logbrush, 0, NULL));
if (i==1)
SetGraphicsMode(hDC, GM_ADVANCED);
Polygon(hDC, P2, 3);
SetGraphicsMode(hDC, GM_COMPATIBLE);
}
{
logbrush.lbColor = RGB(0xFF, 0xFF, 0);
KGDIObject pen (hDC, ExtCreatePen(PS_COSMETIC | PS_SOLID, 1, & logbrush, 0, NULL));
logbrush.lbColor = RGB(0, 0, 0xFF);
KGDIObject brush(hDC, GetStockObject(NULL_BRUSH));
Polygon(hDC, P2, 3);
}
ZoomRect(hDC, -5, -5, 20+8, 15+5, 45, -10, 7);
}
// Poly Fill Mode
for (int t=0; t<2; t++)
{
logbrush.lbColor = RGB(0, 0, 0xFF);
KGDIObject pen (hDC, ExtCreatePen(PS_GEOMETRIC | PS_SOLID | PS_JOIN_MITER, 3, & logbrush, 0, NULL));
if ( t==0 )
SetPolyFillMode(hDC, ALTERNATE);
else
SetPolyFillMode(hDC, WINDING);
for (int m=0; m<4; m++)
{
SetViewportOrgEx(hDC, 120+m*220, 350+t*220, NULL);
const int s0[] = { 4, 4, 100, 0, 100, 1, 100, 2, 100, 3 };
const int s1[] = { 8, 8, 100, 0, 100, 3, 100, 6, 100, 1,
100, 4, 100, 7, 100, 2, 100, 5 };
const int s2[] = { 10, 5, 100, 0, 100, 1, 100, 2, 100, 3, 100, 4,
50, 0, 50, 1, 50, 2, 50, 3, 50, 4 };
const int s3[] = { 10, 5, 100, 0, 100, 1, 100, 2, 100, 3, 100, 4,
50, 4, 50, 3, 50, 2, 50, 1, 50, 0 };
const int * spec[] = { s0, s1, s2, s3 };
POINT P[10];
int n = spec[m][0]; // number of points
int d = spec[m][1]; // number of vertex for each polygon
const int * s = spec[m]+2; // radius, vertex index
for (i=0; i<n; i++)
{
P[i].x = (int) ( s[i*2] * cos(s[i*2+1] * 2 * 3.1415927 / d) );
P[i].y = (int) ( s[i*2] * sin(s[i*2+1] * 2 * 3.1415927 / d) );
}
if ( m<2 )
Polygon(hDC, P, n);
else
{
int V[2] = { 5, 5 };
PolyPolygon(hDC, P, V, 2);
}
}
}
/*
CObject font(hDC, CreateFont(200, 0, 0, 0, FW_HEAVY, FALSE, FALSE, FALSE, DEFAULT_CHARSET, OUT_TT_PRECIS,
CLIP_TT_ALWAYS, PROOF_QUALITY, VARIABLE_PITCH, "MingLiu"));
WCHAR Feng[] = { 'F', 0x5CF0 };
SetBkMode(hDC, TRANSPARENT);
BeginPath(hDC);
TextOutW(hDC, 50, 150, Feng, 2);
EndPath(hDC);
// SetPolyFillMode(hDC, WINDING);
StrokeAndFillPath(hDC);
SetViewportOrgEx(hDC, 0, 0, NULL);
*/
RestoreDC(hDC, nSave);
}
void KMyCanvas::TestFillPath(HDC hDC)
{
const int nPoint = 26;
POINT Point[nPoint];
BYTE Type[nPoint];
// construction a path with two ellipse
BeginPath(hDC);
Ellipse(hDC, -100, -40, 100, 40);
Ellipse(hDC, -40, -100, 40, 100);
EndPath(hDC);
// retrieve path data and rotate 45 degrees
GetPath(hDC, Point, Type, nPoint);
for (int i=0; i<nPoint; i++)
{
double x = Point[i].x * 0.707;
double y = Point[i].y * 0.707;
Point[i].x = (int) (x - y);
Point[i].y = (int) (x + y);
}
KGDIObject brush(hDC, CreateSolidBrush(RGB(0xFF, 0xFF, 0)));
KGDIObject pen (hDC, CreatePen(PS_SOLID, 19, RGB(0, 0, 0xFF)));
for (int t=0; t<8; t++)
{
SetViewportOrgEx(hDC, 120+(t%4)*180, 120+(t/4)*180, NULL);
// constructe the rotated ellipses
BeginPath(hDC);
PolyDraw(hDC, Point, Type, nPoint);
EndPath(hDC);
if ( t>=4 )
SetPolyFillMode(hDC, ALTERNATE);
else
SetPolyFillMode(hDC, WINDING);
switch ( t % 4 )
{
case 0: FillPath(hDC); break;
case 1: StrokeAndFillPath(hDC); break;
case 2: WidenPath(hDC); FillPath(hDC); break;
case 3: WidenPath(hDC);
{
KGDIObject thin(hDC, CreatePen(PS_SOLID, 3, RGB(0, 0, 0xFF)));
StrokeAndFillPath(hDC);
}
}
}
SetViewportOrgEx(hDC, 0, 0, NULL);
}
void KMyCanvas::TestRegion(HDC hDC)
{
KGDIObject brush(hDC, CreateSolidBrush(RGB(0xFF, 0xFF, 0xFF)));
KGDIObject pen (hDC, CreatePen(PS_SOLID, 1, RGB(0, 0, 0xFF)));
HBRUSH red = CreateSolidBrush(RGB(0xFF, 0xFF, 0));
HBRUSH blue = CreateSolidBrush(RGB(0, 0, 0xFF));
for (int i=0; i<6; i++)
{
SetViewportOrgEx(hDC, 150+120*i, 50, NULL);
if ( i & 1 )
{
SetGraphicsMode(hDC, GM_ADVANCED);
Label(hDC, -40, 300, _T("GM_ADVANCED"));
}
else
Label(hDC, -45, 300, _T("GM_COMPATIBLE"));
// Original Drawing Function
switch ( i )
{
case 0:
case 1: Rectangle(hDC, 0, 0, 20, 20); break;
case 2:
case 3: RoundRect(hDC, 0, 0, 20, 20, 10, 10); break;
case 4:
case 5: Ellipse(hDC, 0, 0, 20, 20); break;
}
// Region
HRGN hRgn = NULL;
switch ( i )
{
case 0:
case 1: hRgn = CreateRectRgn(20, 10, 0, 30); break;
case 2:
case 3: hRgn = CreateRoundRectRgn(20, 10, 0, 30, 10, 10); break;
case 4:
case 5: hRgn = CreateEllipticRgn(20, 10, 0, 30); break;
}
PaintRgn(hDC, hRgn);
FrameRgn(hDC, hRgn, red, 1, 1);
DeleteObject(hRgn);
// Path
BeginPath(hDC);
switch ( i )
{
case 0:
case 1: Rectangle(hDC, 0, 20, 20, 40); break;
case 2:
case 3: RoundRect(hDC, 0, 20, 20, 40, 10, 10); break;
case 4:
case 5: Ellipse(hDC, 0, 20, 20, 40); break;
}
EndPath(hDC);
StrokeAndFillPath(hDC);
// PathToRegion
BeginPath(hDC);
switch ( i )
{
case 0:
case 1: Rectangle(hDC, 0, 30, 20, 50); break;
case 2:
case 3: RoundRect(hDC, 0, 30, 20, 50, 10, 10); break;
case 4:
case 5: Ellipse(hDC, 0, 30, 20, 50); break;
}
EndPath(hDC);
hRgn = PathToRegion(hDC);
SetViewportOrgEx(hDC, 0, 0, NULL);
PaintRgn(hDC, hRgn);
FrameRgn(hDC, hRgn, red, 1, 1);
SetViewportOrgEx(hDC, 150+120*i, 50, NULL);
DeleteObject(hRgn);
SetGraphicsMode(hDC, GM_COMPATIBLE);
ZoomRect(hDC, -2, -2, 22, 52, -40, 55, 3);
}
SetViewportOrgEx(hDC, 0, 0, NULL);
Label(hDC, 10, 50 +70, "Original API");
Label(hDC, 10, 100+70, "Region");
Label(hDC, 10, 150+70, "Path");
Label(hDC, 10, 200+70, "PathToRgn");
// Compare Polygon and CreatePolygonRgn
{
SetViewportOrgEx(hDC, 50, 400, NULL);
POINT P[4] = { 0, 0, 0, 20, 30, 20, 30, 0 };
Polygon(hDC, P, 4);
POINT Q[4] = { 0, 25, 0, 45, 30, 45, 30, 25 };
HRGN hRgn = CreatePolygonRgn(Q, 4, ALTERNATE);
PaintRgn(hDC, hRgn);
FrameRgn(hDC, hRgn, red, 1, 1);
DeleteObject(hRgn);
ZoomRect(hDC, -2, -2, 32, 22, 50, 0, 3);
ZoomRect(hDC, -2, 25-2, 32, 25+22, 200, 0, 3);
}
// Compare PathToRgn
{
SetViewportOrgEx(hDC, 420, 400, NULL);
//////////////// Path
BeginPath(hDC);
Ellipse(hDC, 0, 0, 30, 20);
EndPath(hDC);
StrokeAndFillPath(hDC);
/////////////// PathToRegion
BeginPath(hDC);
Ellipse(hDC, 0, 25, 30, 45);
// MoveToEx(hDC, 0, 25, NULL); LineTo(hDC, 30, 25); LineTo(hDC, 30, 45);
EndPath(hDC);
HRGN hRgn = PathToRegion(hDC);
SetViewportOrgEx(hDC, 0, 0, NULL);
PaintRgn(hDC, hRgn);
FrameRgn(hDC, hRgn, blue, 1, 1);
SetViewportOrgEx(hDC, 420, 400, NULL);
DeleteObject(hRgn);
////////// Path, FlattenPath, Poly
BeginPath(hDC);
Ellipse(hDC, 0, 50, 30, 70);
EndPath(hDC);
FlattenPath(hDC);
POINT point[100];
BYTE typ[100];
int n = GetPath(hDC, point, typ, 100);
hRgn = CreatePolygonRgn(point, n, ALTERNATE);
PaintRgn(hDC, hRgn);
FrameRgn(hDC, hRgn, blue, 1, 1);
DeleteObject(hRgn);
ZoomRect(hDC, -2, -2, 32, 22, 50, 0, 3);
ZoomRect(hDC, -2, 25-2, 32, 25+22, 200, 0, 3);
ZoomRect(hDC, -2, 50-2, 32, 50+22, 350, 0, 3);
}
DeleteObject(red);
DeleteObject(blue);
SetViewportOrgEx(hDC, 0, 0, NULL);
}
const TCHAR * TestPtInRegion(int x, int y, HRGN hRegion)
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -