You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

351 lines
7.1 KiB
C++

//////////////////////////////////////////////////////////////////////////////
//文件: CItem类扩展
//主要功能:
// 操作各类元素或完成一定的功能
//
//程序编写: 2006-12-07
//
//
/////////////////////////////////////////////////////////////////////////////
#include "StdAfx.h"
#include "itemtracker.h"
#include "SigmaView.h"
CItemTracker::CItemTracker(CSigmaDoc * ppDoc)
: CItem(ppDoc)
{
Initial();
}
CItemTracker::CItemTracker(void)
: CItem(NULL)
{
Initial();
}
CItemTracker::~CItemTracker(void)
{
}
void CItemTracker::Initial(void)
{
m_HandleSizeFocus=10;
m_HandleSize=8;
m_InnerMargin=0;
m_OuterMargin=0;
m_colorMark=RGB(192, 192, 192);
m_colorHandles=RGB(255, 0, 0);
m_colorCenter=RGB(0, 0, 0);
m_colorTrack=RGB(0, 0, 0);
m_colorHandlesEnableBrush=RGB(255,255,255);
m_colorHandlesDisableBursh=RGB(80,80,80);
m_nDrawMode=TRACKER_CIRCLE;
}
CPoint CItemTracker::GetHandlePoint(int iHandle)
{
// Handles are numbered clockwise, like this:
//
// 0 1 2
// *----------*----------*
// | |
// | |
// 7 * * 8 * 3
// | |
// | |
// *----------*----------*
// 6 5 4
//
// The center point is handle 8, the body is handle 9.
CPoint pt=m_rect.CenterPoint();
switch(iHandle)
{
case 0:
pt.x=m_rect.left;
pt.y=m_rect.top;
break;
case 1:
pt.y=m_rect.top;
break;
case 2:
pt.x=m_rect.right;
pt.y=m_rect.top;
break;
case 3:
pt.x=m_rect.right;
break;
case 4:
pt.x=m_rect.right;
pt.y=m_rect.bottom;
break;
case 5:
pt.y=m_rect.bottom;
break;
case 6:
pt.x=m_rect.left;
pt.y=m_rect.bottom;
break;
case 7:
pt.x=m_rect.left;
break;
case 8:
pt=m_CenterPoint;
break;
}
return pt;
}
// logical coordinates
int CItemTracker::HitTest(CPoint point)
{
if(m_rect.IsRectEmpty())
return HandleNothing;
int i;
for (i = 0; i < 10; i++)
if (GetHandleRect(i).PtInRect(point)) break;
if (i > HandleBody)
i = HandleNothing;
else if (i == HandleCenter && IsCanNotEdit())
i = HandleBody;
if(IsCanNotEdit() && i!=HandleNothing)
i = HandleBody;
return i;
}
CRect CItemTracker::GetTrueRect()
{
CSize sz=GetHandleSize();
CRect rt(m_rect);
rt.InflateRect(sz);
return rt;
}
CRect CItemTracker::GetHandleRect(int iHandle)
{
if (iHandle == HandleBody) return m_rect;
return GetHandleRect(GetHandlePoint(iHandle));
}
CRect CItemTracker::GetHandleRect(CPoint point)
{
return GetHandleRect(point.x,point.y);
}
CSize CItemTracker::GetHandleSize(void)
{
//m_HandleSize=::GetPreferences().WorkaroundHandle.m_nHandleSize;
m_HandleSize = 2;
CSize sz(m_HandleSize,m_HandleSize);
sz.cx+=m_InnerMargin;
sz.cy+=m_InnerMargin;
sz.cx+=m_OuterMargin;
sz.cy+=m_OuterMargin;
return sz;
}
CRect CItemTracker::GetHandleRect(long x,long y)
{
//m_HandleSize=::GetPreferences().WorkaroundHandle.m_nHandleSize;
m_HandleSize = 8;
CRect rc; rc.SetRectEmpty();
rc.OffsetRect(x,y);
int d = m_HandleSize / 2;
rc.InflateRect(d, d);
return rc;
}
CRect CItemTracker::GetHandleRectFocus(CPoint point)
{
return GetHandleRectFocus(point.x,point.y);
}
CRect CItemTracker::GetHandleRectFocus(long x,long y)
{
CRect rc; rc.SetRectEmpty();
rc.OffsetRect(x,y);
int d = GetHandleSizeFocus() / 2;
rc.InflateRect(d, d);
return rc;
}
int CItemTracker::GetHandleSizeFocus(void)
{
//m_HandleSizeFocus=::GetPreferences().WorkaroundHandle.m_nHandleSize+2;
m_HandleSizeFocus = 12;
return m_HandleSizeFocus;
}
void CItemTracker::SetRect(const CRect rect)
{
m_rect=rect;
m_CenterPoint=m_rect.CenterPoint();
}
void CItemTracker::DrawTracker(CDC* pDC)
{
DrawMark(pDC,m_rect,TRUE);
DrawHandle(pDC,GetDrawMode());
if(!IsCanNotEdit())
DrawCenter(pDC,m_CenterPoint,true,true);
}
void CItemTracker::DrawHandle(CDC* pDC, DWORD nDrawMode)
{
int step=1;
if(IsCanNotEdit())
step=2;
CRect rt;
for(int i=0;i<8;i+=step)
{
rt=this->GetHandleRect(i);
DrawHandle(pDC,rt,nDrawMode);
}
}
void CItemTracker::DrawHandle(CDC* pDC, CRect& rect, DWORD nDrawMode)
{
int od=pDC->SetROP2(R2_NOTXORPEN);
CBrush brush,*pOldBrush;
DWORD nNotEdit=TRACKER_NO_EDIT;
if((nDrawMode & nNotEdit) == nNotEdit)
{
brush.CreateSolidBrush(m_colorHandlesDisableBursh);
pOldBrush=(CBrush*)pDC->SelectObject(&brush);
rect.DeflateRect(1,1);//缩小1个
}
else
{
if(nDrawMode & TRACKER_SOLID)
{
brush.CreateSolidBrush(m_colorHandlesEnableBrush);
pOldBrush=(CBrush*)pDC->SelectObject(&brush);
}
else
pOldBrush=(CBrush*)pDC->SelectStockObject(NULL_BRUSH);
}
//m_colorHandles=::GetPreferences().WorkaroundHandle.m_colorHandles;
m_colorHandles = RGB(255, 0, 0);
CPen penHandles(PS_SOLID, 0, m_colorHandles);
CPen* op=(CPen*)pDC->SelectObject(&penHandles);
if(nDrawMode & TRACKER_RECT)
pDC->Rectangle(rect);
else if(nDrawMode & TRACKER_CIRCLE || (nDrawMode & nNotEdit) == nNotEdit)
pDC->Ellipse(&rect);
//pDC->MoveTo(0, 0);
//pDC->LineTo(200, 200);
pDC->SelectObject(pOldBrush);
pDC->SelectObject(op);
if(od>=0)
pDC->SetROP2(od);
}
BOOL CItemTracker::IsCanNotEdit(void)
{
DWORD nNotEdit=TRACKER_NO_EDIT;
if((GetDrawMode() & nNotEdit) == nNotEdit) return TRUE;
return FALSE;
}
void CItemTracker::DrawCenter(CDC * pDC, POINT center, bool bTrack, bool bCenterMove)
{
ASSERT_VALID(pDC);
//m_HandleSize=::GetPreferences().WorkaroundHandle.m_nHandleSize;
m_HandleSize = 4;
CPen pen(PS_SOLID, 0, m_colorCenter);
CGdiObject * pOldPen = pDC->SelectObject(& pen);
CRect rcInside(center, CSize(0, 0));
int d = m_HandleSize / 2;
if (bTrack) d++;
CGdiObject * pOldBrush = pDC->SelectStockObject(NULL_BRUSH);
rcInside.InflateRect(d, d);
pDC->Ellipse(& rcInside);
rcInside.InflateRect(d, d);
CRect rcOutside(rcInside);
pDC->SelectObject(pOldBrush);
rcOutside.InflateRect(m_HandleSize, m_HandleSize);
if (bTrack && bCenterMove)
{
pDC->MoveTo(rcInside.TopLeft());
pDC->LineTo(rcOutside.TopLeft());
pDC->MoveTo(rcInside.right, rcInside.top);
pDC->LineTo(rcOutside.right, rcOutside.top);
pDC->MoveTo(rcInside.BottomRight());
pDC->LineTo(rcOutside.BottomRight());
pDC->MoveTo(rcInside.left, rcInside.bottom);
pDC->LineTo(rcOutside.left, rcOutside.bottom);
}
else
{
pDC->MoveTo(center.x, rcInside.top);
pDC->LineTo(center.x, rcOutside.top);
pDC->MoveTo(rcInside.right, center.y);
pDC->LineTo(rcOutside.right, center.y);
pDC->MoveTo(center.x, rcInside.bottom);
pDC->LineTo(center.x, rcOutside.bottom);
pDC->MoveTo(rcInside.left, center.y);
pDC->LineTo(rcOutside.left, center.y);
}
if (pOldPen) pDC->SelectObject(pOldPen);
}
void CItemTracker::DrawMark(CDC* pDC, CRect rect, BOOL bIsDot)
{
ASSERT_VALID(pDC);
CGdiObject * pOldBrush = pDC->SelectStockObject(NULL_BRUSH);
CPen * pMarkPen = NULL;
if (bIsDot)
{
LOGBRUSH lb;
lb.lbColor = m_colorMark;
lb.lbHatch = 0;
lb.lbStyle = BS_SOLID;
pMarkPen = new CPen(PS_COSMETIC | PS_ALTERNATE, 1, & lb);
}
else pMarkPen = new CPen(PS_SOLID, 0, m_colorMark);
CGdiObject * pOldPen = NULL;
if(pMarkPen) pOldPen = pDC->SelectObject(pMarkPen);
pDC->Rectangle(rect);
if(pOldPen) pDC->SelectObject(pOldPen);
if(pOldBrush) pDC->SelectObject(pOldBrush);
delete pMarkPen;
}
DWORD CItemTracker::SetDrawMode(DWORD nDrawMode)
{
DWORD r=m_nDrawMode;
m_nDrawMode=nDrawMode;
return r;
}
DWORD CItemTracker::GetDrawMode(void)
{
return m_nDrawMode;
}