昵称:烦夫子
类别:界面/平面设计师
年龄:38
现所在地:北京
主页浏览总数:24255
总积分:89
文章数:88
作品数:70
// Shape.cpp: implementation of the Shape class.
// 画装饰
void Shape::FastDraw (CDC* dc, float scale, DrawMode mode, TransformFunc f) const
{
float rr, aa, bb, sa, ea, ang, tmp;
Vector v1, v2, v3, v4, stp, edp;
VectorRun dp;
CPoint pt1, pt2;
CRect rect;
float HoleRadius = 1.0;
float ASRadius = 1.5;
float AHRadius = 1.5;
CPen np(linetype,linewidth,(mode==DNormal)? color : RGB(0,0,0)/*GetColor(mode)*/),*op;
op = dc->SelectObject(&np);
CBrush *old = (CBrush *) dc->SelectStockObject (NULL_BRUSH);
v1 = f (p1);
v2 = f (p2);
v3 = f (p3);
v4 = f (p4);
rr = radius;
sa = stangle;
ea = edangle;
aa = a;
bb = b;
if (shape == SCircle || shape == SArc || shape == SEllipse) {
rr = radius;
sa = stangle;
ea = edangle;
aa = a;
bb = b;
}
switch (shape) {
case SPoint:
v1=dp.WorldToDc(v1);
dc->Ellipse ((v1.x - ASRadius) * scale, (v1.y - ASRadius) * scale, (v1.x + ASRadius) * scale, (v1.y + ASRadius) * scale);
break;
case SLine:
v1 = dp.WorldToDc(v1);
v2 = dp.WorldToDc(v2);
dc->MoveTo (v1.x * scale , v1.y * scale);
dc->LineTo (v2.x * scale , v2.y * scale);
break;
case SRectangle:
v1 = dp.WorldToDc(v1);
v2 = dp.WorldToDc(v2);
v3 = dp.WorldToDc(v3);
v4 = dp.WorldToDc(v4);
dc->MoveTo (v1.x * scale, v1.y * scale);
dc->LineTo (v2.x * scale, v2.y * scale);
dc->LineTo (v3.x * scale, v3.y * scale);
dc->LineTo (v4.x * scale, v4.y * scale);
dc->LineTo (v1.x * scale, v1.y * scale);
break;
case SCircle:
v1=dp.WorldToDc(v1);
dc->Ellipse ((v1.x - rr) * scale, (v1.y - rr) * scale, (v1.x + rr) * scale, (v1.y + rr) * scale);
break;
case SArc:
stp = Vector (cos (sa), sin (sa));
edp = Vector (cos (ea), sin (ea));
v1 = dp.WorldToDc(v1);
pt1 = (stp * rr + v1) * scale;
pt2 = (edp * rr + v1) * scale;
rect.SetRect ((v1.x - rr) * scale, (v1.y - rr) * scale, (v1.x + rr) * scale, (v1.y + rr) * scale);
//Windows GDI function 'ARC' is draw clockwise
if(rect.Width()>=2 && rect.Height()>=2)
dc->Arc (rect, pt1, pt2);
break;
case SEllipse:
v1.DrawEllipse (dc, scale, v1, aa, bb, sa);
break;
case SHole:
{
rr = HoleRadius;
dc->Ellipse ((v1.x - rr) * scale, (v1.y - rr) * scale, (v1.x + rr) * scale, (v1.y + rr) * scale);
CBrush brush((mode==DNormal)? RGB(0,0,255) : RGB(0,0,0)/*GetColor(mode)*/);
CPen pen(PS_SOLID,1,(mode==DNormal)? RGB(0,0,255) : RGB(0,0,0)/*GetColor(mode)*/);
CBrush* ōldb=dc->SelectObject(&brush);
CPen *oldp=dc->SelectObject(&pen);
dc->Ellipse ((v1.x -0.2) * scale, (v1.y - 0.2) * scale, (v1.x +0.2) * scale, (v1.y + 0.2) * scale);
dc->SelectObject(oldp);
dc->SelectObject(oldb);
break;
}
}
dc->SelectObject (old);
dc->SelectObject(op);
}
void Shape::DrawNodes (CDC* dc, float scale, DrawMode mode) const
//显示型值点
{
Vector v;
VectorRun dp;
COLORREF c1, c2;
switch (mode) {
case DNormal:
c1 = RGB (255, 0, 0);
c2 = RGB (0, 0, 255);
break;
case DErase:
c1 = c2 = RGB (255, 255, 255);
break;
default:
return;
}
// draw end points
CPen bluePen (PS_SOLID, 1, c2), *oldPen;
CBrush blueBrush (c2), *oldBrush;
oldPen = dc->SelectObject (&bluePen);
oldBrush = dc->SelectObject (&blueBrush);
switch(shape) {
case SLine:
v = dp.WorldToDc(p1 )* scale;
v.Rectangle (dc, 2);
v = dp.WorldToDc(p2) * scale;
v.Rectangle (dc, 2);
break;
case SCircle:
v = dp.WorldToDc(p1) * scale;
v.Rectangle (dc, 2);
v = dp.WorldToDc((p1 + Vector(radius,0.0f)))* scale;
v.Rectangle (dc, 2);
break;
default:
break;
}
dc->SelectObject (oldPen);
dc->SelectObject (oldBrush);
}
void Shape::DrawBox (CDC* dc, float scale, int index, DrawMode mode) const
//绘被选中状态
{
if (index < 0 || index >= 2)
return;
CPen pen (PS_SOLID, 1, RGB(0,0,0)/*GetColor (mode)*/);
CPen *old = dc->SelectObject (&pen);
dc->SelectStockObject (NULL_BRUSH);
Vector v;
VectorRun dp;
if(index==0) v = dp.WorldToDc(p1) * scale;
else if(index==1) {
if(shape==SLine)
v = dp.WorldToDc(p2) * scale;
else if(shape==SCircle)
v = dp.WorldToDc((p1 + Vector(radius,0.0f))) * scale;
}
else if(index==2) v = dp.WorldToDc(p3) * scale;
else if(index==3) v = dp.WorldToDc(p4) * scale;
v.Rectangle (dc, 5);
dc->SelectObject (old);
}
void Shape::GetMinMax ()
{
float HoleRadius = 1;
switch (shape) {
case SPoint:
MinP = p1 - Vector (1, 1);
MaxP = p1 + Vector (1, 1);
break;
case SLine:
MinP.x = min (p1.x, p2.x);
MinP.y = min (p1.y, p2.y);
MaxP.x = max (p1.x, p2.x);
MaxP.y = max (p1.y, p2.y);
break;
case SRectangle:
MinP.x = min (min (p1.x, p2.x), min (p3.x, p4.x));
MinP.y = min (min (p1.y, p2.y), min (p3.y, p4.y));
MaxP.x = max (max (p1.x, p2.x), max (p3.x, p4.x));
MaxP.y = max (max (p1.y, p2.y), max (p3.y, p4.y));
break;
case SCircle:
case SArc:
MinP = p1 - Vector (radius, radius);
MaxP = p1 + Vector (radius, radius);
break;
case SEllipse:
MinP = p1 - Vector (a, b);
MaxP = p1 + Vector (a, b);
break;
case SHole:
MinP = p1 - Vector (HoleRadius, HoleRadius);
MaxP = p1 + Vector (HoleRadius, HoleRadius);
break;
}
}
float Shape::GetLength () const
{
Vector dp;
VectorRun dp1;
switch (shape) {
case SPoint:
case SRectangle:
return 0.0;
case SLine:
dp = p2 - p1;
return (dp1.Length(dp));
case SCircle:
return PI2*radius;
case SArc:
return (edangle - stangle) * radius;
case SEllipse:
return (PI * a + PI * b);
}
return TRUE;
}
long Shape::GetSize () const
{
return sizeof (Shape);
}
Object& Shape::operator = (const Object& aObject)
{
ASSERT (name == aObject.name);
Shape *p = &((Shape&) aObject);
shape = p->shape;
switch (shape) {
case SPoint:
case SHole:
p1 = p->p1;
break;
case SLine:
p1 = p->p1; p2 = p->p2;
break;
case SRectangle:
p1 = p->p1; p2 = p->p2; p3 = p->p3; p4 = p->p4;
break;
case SCircle:
case SArc:
p1 = p->p1; radius = p->radius; stangle = p->stangle; edangle = p->edangle;
break;
case SEllipse:
p1 = p->p1; a = p->a; b = p->b; stangle = p->stangle; edangle = p->edangle;
break;
}
linetype = aObject.linetype;
color = aObject.color;
linewidth = aObject.linewidth;
plottype = aObject.plottype;
MinP = aObject.MinP;
MaxP = aObject.MaxP;
return *this;
}
BOOL Shape::operator == (const Object& aObject)
{
ASSERT (aObject.name == TShape);
Shape *p = &((Shape&) aObject);
if (shape != p->shape) return FALSE;
switch (shape) {
case SPoint:
return p1 == p->p1;
case SLine:
return p1 == p->p1 && p2 == p->p2;
case SRectangle:
return p1 == p->p1 && p2 == p->p2 && p3 == p->p3 && p4 == p->p4;
case SCircle:
return p1 == p->p1 && radius == p->radius;
case SArc:
return p1 == p->p1 && radius == p->radius && stangle == p->stangle && edangle == p->edangle;
case SEllipse:
return p1 == p->p1 && a == p->a && b == p->b && stangle == p->stangle;
default:
return FALSE;
}
}
BOOL Shape::operator ^ (const Object& aObject)
{
ASSERT (name == aObject.name);
return (shape == ((Shape&) aObject).shape);
}