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.
kev/Drawer/Module/GeoSigmaDraw/ItemBreakCurve.cpp

562 lines
12 KiB
C++

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

#include "StdAfx.h"
#include ".\itembreakcurve.h"
#include "SigmaDoc.h"
#include "SigmaView.h"
#include "ActionListItem.h"
CItemBreakCurve::CItemBreakCurve(CSigmaDoc * ppDoc)
: CItemFocusRect(ppDoc)
, curPos(NULL)
, m_bRange(TRUE)
, m_nActionID(ID_EDIT_TOOL_BREAKS)
, m_bBreak(false)
{
this->SetType(ITEM_BREAK_CURVE);
m_pSelectCurve=new CItemSelectCurve(ppDoc);
m_pSelectCurve->SetNumber(-1);
m_bAutoDelete=TRUE;
m_bNoLineValue=FALSE;
m_bCountSelected = 0;
}
CItemBreakCurve::~CItemBreakCurve(void)
{
Clear();
}
void NItem::CItemBreakCurve::Clear(void)
{
if(m_pSelectCurve)
delete m_pSelectCurve;
m_pSelectCurve=NULL;
}
int CItemBreakCurve::GetSubMenu()
{
return 12;
}
void CItemBreakCurve::OnDraw(CXyDC* pDC)
{
if(m_pSelectCurve)
m_pSelectCurve->OnDraw(pDC);
}
void NItem::CItemBreakCurve::OnDraw(CXyDC* pXyDC, CDC* pDC)
{
OnDraw(pXyDC);
}
void CItemBreakCurve::OnRButtonDown(UINT nFlags, CPoint point)
{
//GetDoc()->DeleteItem();
}
void CItemBreakCurve::OnLButtonDown(CDC *pDC, UINT nFlags, CPoint point, int vk)
{
if (m_pSelectCurve == NULL)
return;
GetDC()->Create(pDC);
if(m_pSelectCurve->GetSelectItem(0)==NULL || m_bRange==FALSE)
{
m_pSelectCurve->OnLButtonDown(pDC, nFlags,point, vk);
if(m_pSelectCurve->GetSelectCount()>1 && !m_bRange)
{
DelList.RemoveAll();
AddList.RemoveAll();
POSITION pos=m_pSelectCurve->GetSelectItem(0);
ASSERT(pos);
CCurveEx* pCurve=(CCurveEx*)GetDoc()->GetDraw()->GetAtValue(pos);
curPos=m_pSelectCurve->GetSelectItem(1);
ASSERT(curPos);
COne* pOne=(COne*)GetDoc()->GetDraw()->GetAt(curPos);
CPoint2D rp=GetDC()->GetReal(point);
if(ProcessCurve(pCurve,pOne,&rp))
{
//UNDO˛Ů×÷
//DelList.AddTail(curPos);
//CActionListItem* pItem=new CActionListItem(GetDoc(),m_nActionID);
//pItem->AddDeleteItem(DelList);
//pItem->AddAddItem(AddList);
//GetDoc()->SetActionItem(pItem);
//DelList.RemoveAll();
//AddList.RemoveAll();
}
m_pSelectCurve->RemoveAt(1);
curPos=NULL;
}
}
else
CItemFocusRect::OnLButtonDown(pDC, nFlags,point, vk);
}
int CItemBreakCurve::OnMouseMove(CDC *pDC, UINT nFlags, CPoint point)
{
if (m_pSelectCurve == NULL)
return 1;
if(m_pSelectCurve->GetSelectItem(0)==NULL || m_bRange==FALSE)
m_pSelectCurve->OnMouseMove(pDC, nFlags,point);
else
CItemFocusRect::OnMouseMove(pDC, nFlags,point);
return 1;
}
void CItemBreakCurve::DoLButtonUp(CDC *pDC)
{
ProcessLButtonUp();
m_bBreak = true;
delete m_pSelectCurve;
m_pSelectCurve = NULL;
}
void NItem::CItemBreakCurve::BreakCurveWithAction(CCurveEx* pCurve, CPositionList& list, CRect8* pRect)
{
DelList.RemoveAll();
AddList.RemoveAll();
BreakCurve(pCurve, list, pRect);
//UNDO˛Ů×÷
if(DelList.GetCount()>0 || AddList.GetCount()>0)
{
CActionListItem* pItem = new CActionListItem(GetDoc(), m_nActionID);
if (DelList.GetCount() > 0)
pItem->AddDeleteItem(DelList);
if (AddList.GetCount() > 0)
{
pItem->AddAddItem(AddList);
GetDoc()->InvalidateSelection(AddList);
}
GetDoc()->SetActionItem(pItem);
}
DelList.RemoveAll();
AddList.RemoveAll();
}
POSITION FindPosition(CPtrList& list, COne* pOther)
{
COne* pOne;
POSITION pb, pt;
pt=list.GetHeadPosition();
while(pt)
{
pb=pt;
pOne=(COne*)list.GetNext(pt);
if(pOne==pOther) return pb;
}
return NULL;
}
void NItem::CItemBreakCurve::BreakAllEditableCurve(CPositionList& list)
{
DelList.RemoveAll();
AddList.RemoveAll();
COne* pOne;
//ťńľĂËůÓĐÇúĎß
CPtrList pl;
POSITION pos,pt;
pos=list.GetHeadPosition();
while(pos)
{
pt=list.GetNext(pos);
pOne=GetDoc()->GetDraw()->GetAt(pt);
if(!pOne->IsCanEdit() || !pOne->IsView()) continue;
if(pOne->GetType()!=DOUBLEFOX_CURVE) continue;
pl.AddTail(pOne);
}
double len=pl.GetCount();
long count=0;
//GetDoc()->BeginProgress(ID_LAYERTREE_BREAK_CURVE);
pos=pl.GetHeadPosition();
while(pos)
{
AfxGetPublicFunction()->SetProgressPos(AfxGetPublicFunction()->FloatToLong(++count/len*100));
pOne=(COne*)pl.GetNext(pos);
BreakOne(pOne, pl);
//UNDO˛Ů×÷
if(DelList.GetCount()>0 || AddList.GetCount()>0)
{
CActionListItem* pItem=new CActionListItem(GetDoc(),ID_LAYERTREE_BREAK_CURVE);
if(DelList.GetCount()>0)
pItem->AddDeleteItem(DelList);
if(AddList.GetCount()>0)
{
pItem->AddAddItem(AddList);
GetDoc()->InvalidateSelection(AddList);
}
GetDoc()->SetActionItem(pItem);
GetDoc()->Modified();
}
DelList.RemoveAll();
AddList.RemoveAll();
}
//GetDoc()->EndProgress();
}
bool NItem::CItemBreakCurve::IsBreaked()
{
return m_bBreak;
}
int NItem::CItemBreakCurve::GetSelectCount()
{
if (m_pSelectCurve == NULL)
return 0;
return m_pSelectCurve->GetSelectCount();
}
void CItemBreakCurve::HightLightFirstCurve()
{
POSITION pos = m_pSelectCurve->GetSelectItem(0);
if (pos == 0)
return;
m_pSelectCurve->DrawSelectItem(pos);
}
void NItem::CItemBreakCurve::ProcessLButtonUp(void)
{
if (m_pSelectCurve == NULL)
return;
POSITION pos = m_pSelectCurve->GetSelectItem(0);
//ASSERT(pos != NULL);
if (pos == NULL)
return;
COne* pOne = (COne*)GetDoc()->GetDraw()->GetAt(pos);
CCurveEx* pCurve = (CCurveEx*)pOne->GetValue();
CRect8 rect = this->GetRect();
CPositionList list;
GetDoc()->GetDraw()->IsInRange(rect, list);
if (list.GetCount() == 0) return;
BreakCurveWithAction(pCurve, list, &rect);
}
int NItem::CItemBreakCurve::BreakOne(COne* pBaseOne, CPtrList& allBaseCurveList)
{
CRect8 rect;
CCurveEx* pCurve=(CCurveEx*)pBaseOne->GetValue();
rect=pBaseOne->GetRect();
CPositionList select;
if(GetDoc()->GetDraw()->IsInRange(rect, select)==0) return 0;
COne *pOther;
//ČĽłýˇśÎ§ĎßąžÉí
POSITION ps, pb, pg;
ps=select.GetHeadPosition();
while(ps)
{
pg=ps;
pb=select.GetNext(ps);
pOther=GetDoc()->GetDraw()->GetAt(pb);
if(pOther->GetType()!=DOUBLEFOX_CURVE)
select.RemoveAt(pg);
else if(FindPosition(allBaseCurveList, pOther))
select.RemoveAt(pg);
}
//´ňśĎÇúĎß
BreakCurve(pCurve, select, &rect);
return 1;
}
void NItem::CItemBreakCurve::BreakCurve(CCurveEx* pCurve, CPositionList& list, CRect8* pRect)
{
COne* pOne;
CCurveEx* pc;
CPoint2D rp;
CPoint2D tp;
CPoint2D* pCenterPoint=NULL;
POSITION p;
p=list.GetHeadPosition();
while(p)
{
curPos=list.GetNext(p);
pOne=(COne*)GetDoc()->GetDraw()->GetAt(curPos);
if(pOne->GetType()!=DOUBLEFOX_CURVE) continue;
//źĆËă×î˝üľÄľă
pc=(CCurveEx*)pOne->GetValue();
if(pc==pCurve) continue;
if(pRect)
{
rp=pRect->CenterPoint();
for(int i=0;i<pc->num; i++)
{
tp.SetPoint(pc->x[i], pc->y[i]);
if(pRect->PtInRect(tp))
{
rp=tp;
break;
}
}
pCenterPoint=&rp;
}
if(ProcessCurve(pCurve,pOne,pCenterPoint))
DelList.AddTail(curPos);
}
}
int CItemBreakCurve::ProcessCurve(CCurveEx* pCurve, COne* pOne, CPoint2D* pPoint)
{
//´ňśĎÇúĎß
CCurveEx* pBreakCurve=(CCurveEx*)pOne->GetValue();
CCrossList list;
pBreakCurve->Cross(*(CCurve*)pCurve, list);
if(list.GetCount()==0) return 0;
BOOL bDoubleHeadTail=!m_bNoLineValue;
int count=0;
double zero=1e-300;
CCrossPoint p1,p2;
p1=list.GetHead();
if(list.GetCount()==1) //ÎŞÁˡŔÖšÖظ´´ňśĎĘą,ŇýĆđ´ňśĎşóľÄÇúĎ߽ھăČŤ˛żÎŞÍŹŇť×řąęľÄÇéżö
{
if(fabs(pBreakCurve->l[0]-p1.x[0])<1e-10) return 0;
if(fabs(pBreakCurve->l[pBreakCurve->num-1]-p1.x[0])<1e-10) return 0;
}
pBreakCurve->GetCurve(pBreakCurve->l[0],p1.x[0]-zero,PointList, bDoubleHeadTail, m_bNoLineValue);
if(bDoubleHeadTail && !PointList.IsEmpty()) PointList.RemoveHead();
if(AddCurve(pOne)) count++;
POSITION pos=list.GetHeadPosition();
list.GetNext(pos);
while(pos)
{
p2=list.GetNext(pos);
pBreakCurve->GetCurve(p1.x[0]-zero,p2.x[0]-zero,PointList, bDoubleHeadTail, m_bNoLineValue);
if(AddCurve(pOne)) count++;
p1=p2;
}
pBreakCurve->GetCurve(p1.x[0]-zero,pBreakCurve->l[pBreakCurve->num-1],PointList, bDoubleHeadTail, m_bNoLineValue);
if(bDoubleHeadTail && !PointList.IsEmpty()) PointList.RemoveTail();
if(AddCurve(pOne)) count++;
return count;
}
POSITION CItemBreakCurve::AddCurve(COne* pBaseOne)
{
if(PointList.GetCount()<2 ) return NULL;
//Čçšű´ňśĎşóľÄÇúĎßËůÓнھă×řąęČŤĎŕÍŹĘą˛ťÔöźÓ
BOOL bDelete=TRUE;
POSITION pos=PointList.GetHeadPosition();
dfPoint dp, prevdp;
prevdp=PointList.GetNext(pos);
while(pos)
{
dp=PointList.GetNext(pos);
if(AfxGetPublicFunction()->Distance2(dp.x0, dp.y0, prevdp.x0, prevdp.y0)>1e-10)
{
bDelete=FALSE;
break;
}
prevdp=dp;
}
if(bDelete) return NULL;
CCurveEx* pBreakCurve=(CCurveEx*)pBaseOne->GetValue();
CCurveEx* pCurve=new CCurveEx((long)PointList.GetCount());
pCurve->CloneOtherParameter(*pBreakCurve);
pCurve->SetPoints(PointList,pBreakCurve->nPoint,pBreakCurve->bAutoLocation);
PointList.RemoveAll();
return AddCurve(pBaseOne,pCurve);
}
POSITION CItemBreakCurve::AddCurve(COne* pBaseOne, CCurveEx* pCurve)
{
if(curPos==NULL) return NULL;
COne *pOne=new COne;
pOne->SetType(pBaseOne->GetType());
pOne->value=pCurve;
pOne->SetLayer(pBaseOne->GetLayer());
if(pBaseOne->HowToViewCurve)
{
pOne->HowToViewCurve=new CHowToViewCurve();
*pOne->HowToViewCurve=*pBaseOne->HowToViewCurve;
}
if(pBaseOne->HowToViewPoint)
{
pOne->HowToViewPoint=new CHowToViewPoint();
*pOne->HowToViewPoint=*pBaseOne->HowToViewPoint;
}
pOne->color=pBaseOne->color;
if(pBaseOne->pHyperlink)
{
pOne->pHyperlink=new CHyperlinkMulti;
*pOne->pHyperlink=*pBaseOne->pHyperlink;
}
POSITION pos=InsertElementBefore(curPos,pOne,FALSE);
AddList.AddTail(pos);
return pos;
}
void CItemBreakCurve::sort_location(CList<CCrossPoint,CCrossPoint> &xy,CCrossPoint &cp,int nSortIndex)
{
int i,num;
CCrossPoint t;
POSITION p;
num=(int)xy.GetCount();
if(num<1)
{
xy.AddTail(cp);
return;
}
p=xy.GetHeadPosition( );
t=xy.GetAt(p);
if(cp.x[nSortIndex]<t.x[nSortIndex])
{
xy.AddHead(cp);
return;
}
if(num==1)
{
xy.AddTail(cp);
return;
}
for(i=0;i<num-1;++i)
{
xy.GetNext(p);
t=xy.GetAt(p);
if(cp.x[nSortIndex]<t.x[nSortIndex])
{
xy.InsertBefore(p,cp);
return;
}
}
xy.AddTail(cp);
}
void CItemBreakCurve::SortLocation(CList<CCrossPoint,CCrossPoint> &xy, int nSortIndex)
{
if((int)xy.GetCount()<1) return;
CCrossPoint t;
CList<CCrossPoint,CCrossPoint> list;
POSITION p;
p=xy.GetHeadPosition();
while(p)
{
t=xy.GetNext(p);
list.AddTail(t);
}
xy.RemoveAll();
p=list.GetHeadPosition();
while(p)
{
t=list.GetNext(p);
sort_location(xy,t,nSortIndex);
}
}
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//class CItemBreakCurveDirect
CItemBreakCurveDirect::CItemBreakCurveDirect(CSigmaDoc * ppDoc)
: CItemBreakCurve(ppDoc)
//m_buttonStatus(0)
{
this->SetType(ITEM_BREAK_CURVE_DIRECT);
m_pItemCurve=new CItemCurve(ppDoc);
}
CItemBreakCurveDirect::~CItemBreakCurveDirect()
{
Clear();
}
void NItem::CItemBreakCurveDirect::Clear(void)
{
CItemBreakCurve::Clear();
if(m_pItemCurve) delete m_pItemCurve;
m_pItemCurve=NULL;
}
void NItem::CItemBreakCurveDirect::OnDraw(CXyDC* pXyDC, CDC* pDC)
{
m_pItemCurve->OnDraw(pXyDC, pDC);
}
void CItemBreakCurveDirect::OnLButtonDown(CDC *pDC, UINT nFlags, CPoint point, int vk)
{
int count = m_pItemCurve->PointList.GetCount();
if (count < 2)
{
m_pItemCurve->OnLButtonDown(pDC, nFlags, point, vk);
}
count = m_pItemCurve->PointList.GetCount();
if (count == 2) {
CCurveEx * pCurve = new CCurveEx;
pCurve->SetPoints(m_pItemCurve->PointList, 2, TRUE);
m_pItemCurve->Reset();
if (pCurve->num < 2)
{
delete pCurve;
return;
}
CRect8 rt(1e300, -1e300, -1e300, 1e300);
pCurve->GetRange(rt);
rt.NormalizeRect();
//ŃĄÔńÖąĎßśÎÍâ°üžŘĐÎÄÚľÄĎßśÎ.
CPositionList list;
GetDoc()->GetDraw()->IsInRange(rt, list);
if (list.GetCount() == 0)
return;
BreakCurveWithAction(pCurve, list, NULL);
delete pCurve;
}
}
int CItemBreakCurveDirect::OnMouseMove(CDC* pDC, UINT nFlags, CPoint point)//, BYTE*& destBuffer, int& destLen)
{
return m_pItemCurve->OnMouseMove(pDC, nFlags, point);
}
void CItemBreakCurveDirect::OnRButtonDown(UINT nFlags, CPoint point)
{
}
BOOL CItemBreakCurveDirect::OnKeyUp(UINT nChar, UINT nRepCnt, UINT nFlags)
{
if (nChar != VK_ESCAPE)
return FALSE;
if (m_pScreenDC == 0)
return FALSE;
if (m_pItemCurve->PointList.IsEmpty())
return TRUE;
m_pItemCurve->Reset();
return TRUE;
}
void CItemBreakCurveDirect::OnLButtonUp(CDC* pDC, UINT nFlags, CPoint point, int vk)
{
}