
展开全部
切换旋转坐标系后,画正常的椭圆不就可以了?
把点定位于椭圆中心点,旋转坐标,画
用过GDIPlus的路过
把点定位于椭圆中心点,旋转坐标,画
用过GDIPlus的路过
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
利用外切矩形计算倾斜度,然后旋转
// Create points to simulate ellipse using beziers
//使用贝塞尔曲线创建点,模拟椭圆
void EllipseToBezier(CRect& r, CPoint* cCtlPt)
{
// MAGICAL CONSTANT to map ellipse to beziers
// 2/3*(sqrt(2)-1)
// 把椭圆映射为贝塞尔曲线的常量 2/3*(sqrt(2)-1)
const double EToBConst = 0.2761423749154;
CSize offset((int)(r.Width() * EToBConst), (int)(r.Height() * EToBConst));
// Use the following line instead for mapping systems where +ve Y is upwards
// 在Y轴正方向向上时,使用下面一行
// CSize offset((int)(r.Width() * EToBConst), -(int)(r.Height() * EToBConst));
CPoint centre((r.left + r.right) / 2, (r.top + r.bottom) / 2);
cCtlPt[0].x = //------------------------/
cCtlPt[1].x = // /
cCtlPt[11].x = // 2___3___4 /
cCtlPt[12].x = r.left; // 1 5 /
cCtlPt[5].x = // | | /
cCtlPt[6].x = // | | /
cCtlPt[7].x = r.right; // 0,12 6 /
cCtlPt[2].x = // | | /
cCtlPt[10].x = centre.x - offset.cx; // | | /
cCtlPt[4].x = // 11 7 /
cCtlPt[8].x = centre.x + offset.cx; // 10___9___8 /
cCtlPt[3].x = // /
cCtlPt[9].x = centre.x; //------------------------*
cCtlPt[2].y =
cCtlPt[3].y =
cCtlPt[4].y = r.top;
cCtlPt[8].y =
cCtlPt[9].y =
cCtlPt[10].y = r.bottom;
cCtlPt[7].y =
cCtlPt[11].y = centre.y + offset.cy;
cCtlPt[1].y =
cCtlPt[5].y = centre.y - offset.cy;
cCtlPt[0].y =
cCtlPt[12].y =
cCtlPt[6].y = centre.y;
}
Rotation of the Ellipse can be accomplished using code similar to:
使用与下面近似的代码可完成椭圆的旋转
// LDPoint is an equivalent type to CPoint but with floating point precision
// LDPoint是一个和CPoint相当的类型,不过它还具有浮点精度。
void Rotate(double radians, const CPoint& c, CPoint* vCtlPt, unsigned Cnt)
{
double sinAng = sin(radians);
double cosAng = cos(radians);
LDPoint constTerm( c.x - c.x * cosAng - c.y * sinAng,
c.y + c.x * sinAng - c.y * cosAng);
for (int i = Cnt-1; i>=0; --i)
{
vCtlPt[i] = (LDPoint( vCtlPt[i].x * cosAng + vCtlPt[i].y * sinAng,
-vCtlPt[i].x * sinAng + vCtlPt[i].y * cosAng) + constTerm).GetCPoint();
}
}
// Create Ellipse
// 创建椭圆
CRect rect; GetClientRect(&rect);
CPoint ellipsePts[13];
EllipseToBezier(ellipseR, ellipsePts);
// Rotate
// 旋转
Rotate(m_Radians, midPoint, ellipsePts, 13);
Filled Ellipses
Of course, four bezier curves together only make up the outline of an ellipse, whether rotated or not. Thankfully, Win32 Path functions are there for filled ellipses. One only needs to enclose the PolyBezier(...) call in a Path Bracket. The resulting path can be stroked and filled to one's satisfaction. If one is feeling adventurous, further special fills like gradients, custom bitmaps or fractals etc. can be achieved by first setting the clipping region to the path via SelectClipPath(...).
填充椭圆
当然,无论是不是旋转,四条贝塞尔曲线只完成了椭圆的轮廓。幸运的是,Win32路径功能可用于填充椭圆。你只在需要调用PolyBezier(...)来封闭路径。完成的路径是一笔画出的,而且能被让人满意的填充。假如有人觉得还不够,比如更特殊的填充,比如斜线、用户位图或不规则碎片等。这些能由SelectClipPath(...)来把剪贴区域设置到路径上来而获得。
dc.BeginPath();
dc.PolyBezier(ellipsePts);
dc.EndPath();
dc.StrokePath;
// or FillPath();
// or StrokeAndFillPath();
// or PathToRegion(dc.m_hDC);
//
//或者 FillPath();
//或者StrokeAndFillPath();
//或者PathToRegion(dc.m_hDC);
// Create points to simulate ellipse using beziers
//使用贝塞尔曲线创建点,模拟椭圆
void EllipseToBezier(CRect& r, CPoint* cCtlPt)
{
// MAGICAL CONSTANT to map ellipse to beziers
// 2/3*(sqrt(2)-1)
// 把椭圆映射为贝塞尔曲线的常量 2/3*(sqrt(2)-1)
const double EToBConst = 0.2761423749154;
CSize offset((int)(r.Width() * EToBConst), (int)(r.Height() * EToBConst));
// Use the following line instead for mapping systems where +ve Y is upwards
// 在Y轴正方向向上时,使用下面一行
// CSize offset((int)(r.Width() * EToBConst), -(int)(r.Height() * EToBConst));
CPoint centre((r.left + r.right) / 2, (r.top + r.bottom) / 2);
cCtlPt[0].x = //------------------------/
cCtlPt[1].x = // /
cCtlPt[11].x = // 2___3___4 /
cCtlPt[12].x = r.left; // 1 5 /
cCtlPt[5].x = // | | /
cCtlPt[6].x = // | | /
cCtlPt[7].x = r.right; // 0,12 6 /
cCtlPt[2].x = // | | /
cCtlPt[10].x = centre.x - offset.cx; // | | /
cCtlPt[4].x = // 11 7 /
cCtlPt[8].x = centre.x + offset.cx; // 10___9___8 /
cCtlPt[3].x = // /
cCtlPt[9].x = centre.x; //------------------------*
cCtlPt[2].y =
cCtlPt[3].y =
cCtlPt[4].y = r.top;
cCtlPt[8].y =
cCtlPt[9].y =
cCtlPt[10].y = r.bottom;
cCtlPt[7].y =
cCtlPt[11].y = centre.y + offset.cy;
cCtlPt[1].y =
cCtlPt[5].y = centre.y - offset.cy;
cCtlPt[0].y =
cCtlPt[12].y =
cCtlPt[6].y = centre.y;
}
Rotation of the Ellipse can be accomplished using code similar to:
使用与下面近似的代码可完成椭圆的旋转
// LDPoint is an equivalent type to CPoint but with floating point precision
// LDPoint是一个和CPoint相当的类型,不过它还具有浮点精度。
void Rotate(double radians, const CPoint& c, CPoint* vCtlPt, unsigned Cnt)
{
double sinAng = sin(radians);
double cosAng = cos(radians);
LDPoint constTerm( c.x - c.x * cosAng - c.y * sinAng,
c.y + c.x * sinAng - c.y * cosAng);
for (int i = Cnt-1; i>=0; --i)
{
vCtlPt[i] = (LDPoint( vCtlPt[i].x * cosAng + vCtlPt[i].y * sinAng,
-vCtlPt[i].x * sinAng + vCtlPt[i].y * cosAng) + constTerm).GetCPoint();
}
}
// Create Ellipse
// 创建椭圆
CRect rect; GetClientRect(&rect);
CPoint ellipsePts[13];
EllipseToBezier(ellipseR, ellipsePts);
// Rotate
// 旋转
Rotate(m_Radians, midPoint, ellipsePts, 13);
Filled Ellipses
Of course, four bezier curves together only make up the outline of an ellipse, whether rotated or not. Thankfully, Win32 Path functions are there for filled ellipses. One only needs to enclose the PolyBezier(...) call in a Path Bracket. The resulting path can be stroked and filled to one's satisfaction. If one is feeling adventurous, further special fills like gradients, custom bitmaps or fractals etc. can be achieved by first setting the clipping region to the path via SelectClipPath(...).
填充椭圆
当然,无论是不是旋转,四条贝塞尔曲线只完成了椭圆的轮廓。幸运的是,Win32路径功能可用于填充椭圆。你只在需要调用PolyBezier(...)来封闭路径。完成的路径是一笔画出的,而且能被让人满意的填充。假如有人觉得还不够,比如更特殊的填充,比如斜线、用户位图或不规则碎片等。这些能由SelectClipPath(...)来把剪贴区域设置到路径上来而获得。
dc.BeginPath();
dc.PolyBezier(ellipsePts);
dc.EndPath();
dc.StrokePath;
// or FillPath();
// or StrokeAndFillPath();
// or PathToRegion(dc.m_hDC);
//
//或者 FillPath();
//或者StrokeAndFillPath();
//或者PathToRegion(dc.m_hDC);
追问
额....这个旋转外切矩形的倾斜度具体该怎么写?我的思路也是这样的...
本回答被网友采纳
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询