301 lines
7.6 KiB
C++
301 lines
7.6 KiB
C++
#include "stdafx.h"
|
|
#include <set>
|
|
#include "DimScaleZoneDlg.h"
|
|
#include "coretools.h"
|
|
#include "AecDbDimScaleZone.h"
|
|
#include "KTModelLayoutXData.h"
|
|
namespace
|
|
{
|
|
struct COMPARE_ZONE_AREA
|
|
{
|
|
bool operator () (const AecDbDimScaleZone *p1, const AecDbDimScaleZone *p2) const
|
|
{
|
|
return p1->GetArea() < p2->GetArea();
|
|
}
|
|
};
|
|
}
|
|
|
|
IMPLEMENT_DYNAMIC(CDimScaleZoneDlg, CDialog)
|
|
|
|
CDimScaleZoneDlg::CDimScaleZoneDlg(CWnd* pParent )
|
|
: CDialog(IDD_DIM_SCALE_ZONE_DLG, pParent)
|
|
, m_iNumerator(1)
|
|
, m_iDenominator(100)
|
|
, m_iDrawUnits(0)
|
|
, m_iDimUnits(0)
|
|
{
|
|
struct resbuf rb;
|
|
acedGetVar(_T("INSUNITS"), &rb);
|
|
m_iDrawUnits = getIdxByUnits((AcDb::UnitsValue)rb.resval.rint);
|
|
m_iDimUnits = m_iDrawUnits;
|
|
|
|
AecDbObjXDataMap xDataMap;
|
|
CString scale(_T("1:100"));
|
|
xDataMap.SetAt(DOC_SCALE, scale); //出图比例
|
|
if (KTModelLayoutXData::ReadModelXData(KT_PIPEINIT, xDataMap)
|
|
&& xDataMap.GetAt(DOC_SCALE, scale))
|
|
{
|
|
std::vector<CString> ss;
|
|
CoreTools::SplitString(scale, _T(':'), ss);
|
|
if (ss.size() == 2)
|
|
{
|
|
m_iNumerator = _ttoi(ss[0]);
|
|
m_iDenominator = _ttoi(ss[1]);
|
|
}
|
|
}
|
|
}
|
|
|
|
CDimScaleZoneDlg::CDimScaleZoneDlg(const int &numerator
|
|
, const int &denominator
|
|
, const AcDb::UnitsValue &drawUnits
|
|
, const AcDb::UnitsValue &dimUnits
|
|
, CWnd *pParent)
|
|
: CDialog(IDD_DIM_SCALE_ZONE_DLG, pParent)
|
|
, m_iNumerator(numerator)
|
|
, m_iDenominator(denominator)
|
|
{
|
|
m_iDrawUnits = getIdxByUnits(drawUnits);
|
|
m_iDimUnits = getIdxByUnits(dimUnits);
|
|
}
|
|
|
|
CDimScaleZoneDlg::~CDimScaleZoneDlg() { }
|
|
|
|
void CDimScaleZoneDlg::DoDataExchange(CDataExchange* pDX)
|
|
{
|
|
CDialog::DoDataExchange(pDX);
|
|
DDX_Text(pDX, IDC_EDT_MOLECULAR, m_iNumerator);
|
|
DDV_MinMaxInt(pDX, m_iNumerator, 1, INT_MAX);
|
|
DDX_Text(pDX, IDC_EDT_DENOMINATOR, m_iDenominator);
|
|
DDV_MinMaxInt(pDX, m_iDenominator, 1, INT_MAX);
|
|
DDX_CBIndex(pDX, IDC_CMB_DRAW, m_iDrawUnits);
|
|
DDX_CBIndex(pDX, IDC_CMB_DIM, m_iDimUnits);
|
|
}
|
|
|
|
BOOL CDimScaleZoneDlg::OnInitDialog()
|
|
{
|
|
CDialog::OnInitDialog();
|
|
|
|
UpdateData(FALSE);
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
BEGIN_MESSAGE_MAP(CDimScaleZoneDlg, CDialog)
|
|
ON_BN_CLICKED(IDOK, &CDimScaleZoneDlg::OnBnClickedOk)
|
|
END_MESSAGE_MAP()
|
|
|
|
AcDb::UnitsValue CDimScaleZoneDlg::getUnitsByIdx(const int &idx)
|
|
{
|
|
// 毫米; 米; 厘米; 分米; 公里; 英寸; 英尺; 码; 英里;
|
|
switch (idx)
|
|
{
|
|
case 0: return AcDb::kUnitsMillimeters;
|
|
case 1: return AcDb::kUnitsMeters;
|
|
case 2: return AcDb::kUnitsCentimeters;
|
|
case 3: return AcDb::kUnitsDecimeters;
|
|
case 4: return AcDb::kUnitsKilometers;
|
|
case 5: return AcDb::kUnitsInches;
|
|
case 6: return AcDb::kUnitsFeet;
|
|
case 7: return AcDb::kUnitsYards;
|
|
case 8: return AcDb::kUnitsMiles;
|
|
default: break;
|
|
}
|
|
return AcDb::kUnitsUndefined;
|
|
}
|
|
|
|
int CDimScaleZoneDlg::getIdxByUnits(const AcDb::UnitsValue &un)
|
|
{
|
|
switch (un)
|
|
{
|
|
case AcDb::kUnitsMillimeters: return 0;
|
|
case AcDb::kUnitsMeters: return 1;
|
|
case AcDb::kUnitsCentimeters: return 2;
|
|
case AcDb::kUnitsDecimeters: return 3;
|
|
case AcDb::kUnitsKilometers: return 4;
|
|
case AcDb::kUnitsInches: return 5;
|
|
case AcDb::kUnitsFeet: return 6;
|
|
case AcDb::kUnitsYards: return 7;
|
|
case AcDb::kUnitsMiles: return 8;
|
|
default: break;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
void CDimScaleZoneDlg::OnBnClickedOk()
|
|
{
|
|
if (!UpdateData(TRUE))
|
|
return;
|
|
|
|
CDialog::OnOK();
|
|
}
|
|
|
|
int CDimScaleZoneDlg::getNumerator()
|
|
{
|
|
return m_iNumerator;
|
|
}
|
|
|
|
int CDimScaleZoneDlg::getDenominator()
|
|
{
|
|
return m_iDenominator;
|
|
}
|
|
|
|
AcDb::UnitsValue CDimScaleZoneDlg::getDrawUnits()
|
|
{
|
|
return getUnitsByIdx(m_iDrawUnits);
|
|
}
|
|
|
|
AcDb::UnitsValue CDimScaleZoneDlg::getDimUnits()
|
|
{
|
|
return getUnitsByIdx(m_iDimUnits);
|
|
}
|
|
|
|
////////////////////////////////////////////////////////////////////////////////////
|
|
|
|
void CDimScaleZoneDlg::start()
|
|
{
|
|
ads_point adsPtFirst;
|
|
if (acedGetPoint(NULL, _T("\n选择比例范围的第一个点:"), adsPtFirst) != RTNORM) return;
|
|
|
|
XDimScaleZoneJig jig;
|
|
jig.m_ptTL = asPnt3d(adsPtFirst);
|
|
CoreTools::UCS2WCS(jig.m_ptTL, jig.m_ptTL);
|
|
AcEdJig::DragStatus stat = jig.DoIt();
|
|
if (stat != AcEdJig::kNormal) return;
|
|
|
|
CAcModuleResourceOverride myResources;
|
|
CDimScaleZoneDlg dlg;
|
|
if (dlg.DoModal() != IDOK) return;
|
|
|
|
AcGePoint3d ptTL(jig.m_ptTL)
|
|
, ptTR(jig.m_ptTR)
|
|
, ptBL(jig.m_ptBL)
|
|
, ptBR(jig.m_ptBR);
|
|
CoreTools::WCS2UCS(ptTL, ptTL);
|
|
CoreTools::WCS2UCS(ptTR, ptTR);
|
|
CoreTools::WCS2UCS(ptBL, ptBL);
|
|
CoreTools::WCS2UCS(ptBR, ptBR);
|
|
// 在 UCS下重新排列四个点,按照从左到右,从上到下顺序
|
|
std::set<double> xset, yset;
|
|
xset.insert(ptTL.x);
|
|
xset.insert(ptTR.x);
|
|
xset.insert(ptBL.x);
|
|
xset.insert(ptBR.x);
|
|
yset.insert(ptTL.y);
|
|
yset.insert(ptTR.y);
|
|
yset.insert(ptBL.y);
|
|
yset.insert(ptBR.y);
|
|
double xBig(*xset.rbegin()), xSml(*xset.begin());
|
|
double yBig(*yset.rbegin()), ySml(*yset.begin());
|
|
|
|
ptTL.x = xSml; ptTL.y = yBig;
|
|
ptTR.x = xBig; ptTR.y = yBig;
|
|
ptBL.x = xSml; ptBL.y = ySml;
|
|
ptBR.x = xBig; ptBR.y = ySml;
|
|
|
|
CoreTools::UCS2WCS(ptTL, ptTL);
|
|
CoreTools::UCS2WCS(ptBL, ptBL);
|
|
CoreTools::UCS2WCS(ptBR, ptBR);
|
|
CoreTools::UCS2WCS(ptTR, ptTR);
|
|
|
|
AecDbDimScaleZone *pZon(new AecDbDimScaleZone);
|
|
pZon->SetTopLeftPoint(ptTL);
|
|
pZon->SetTopRightPoint(ptTR);
|
|
pZon->SetBottomLeftPoint(ptBL);
|
|
pZon->SetBottomRightPoint(ptBR);
|
|
pZon->SetNumerator(dlg.getNumerator());
|
|
pZon->SetDenominator(dlg.getDenominator());
|
|
pZon->SetDrawUnits(dlg.getDrawUnits());
|
|
pZon->SetDimUnits(dlg.getDimUnits());
|
|
|
|
CoreTools::AddToModelSpace(pZon);
|
|
}
|
|
|
|
void CDimScaleZoneDlg::dbl()
|
|
{
|
|
extern bool GetDoubleClickEnt(LPCTSTR pszCmd, AcDbObjectId& id);
|
|
AcDbObjectId id;
|
|
bool bIsOk = GetDoubleClickEnt(_T("DBL_AEC_DIMSCALEZONE"), id);
|
|
if (!bIsOk || !id.isValid()) return;
|
|
|
|
AcDbObjectPointer<AecDbDimScaleZone> ent(id, AcDb::kForWrite);
|
|
if (ent.openStatus() != Acad::eOk) return;
|
|
|
|
CAcModuleResourceOverride myResources;
|
|
CDimScaleZoneDlg dlg(ent->GetNumerator()
|
|
, ent->GetDenominator()
|
|
, (AcDb::UnitsValue)ent->GetDrawUnits()
|
|
, (AcDb::UnitsValue)ent->GetDimUnits());
|
|
if (dlg.DoModal() != IDOK) return;
|
|
|
|
ent->SetNumerator(dlg.getNumerator());
|
|
ent->SetDenominator(dlg.getDenominator());
|
|
ent->SetDrawUnits(dlg.getDrawUnits());
|
|
ent->SetDimUnits(dlg.getDimUnits());
|
|
}
|
|
|
|
bool CDimScaleZoneDlg::hitTest(const AcGePoint3d &pt
|
|
, double &dScale
|
|
, AcDb::UnitsValue &drawUnits
|
|
, AcDb::UnitsValue &dimUnits)
|
|
{
|
|
struct resbuf *pRb = acutBuildList(RTDXF0, _T("AEC_DIMSCALEZONE"), 0);
|
|
ads_name ss, ent;
|
|
acedSSGet(_T("A"), NULL, NULL, pRb, ss);
|
|
Adesk::Int32 lLen = 0;
|
|
acedSSLength(ss, &lLen);
|
|
AcDbObjectId id;
|
|
AcDbObjectIdArray arIds;
|
|
std::set<AcDbObjectPointer<AecDbDimScaleZone>> dszs;
|
|
for (int i(0); i < lLen; ++i)
|
|
{
|
|
acedSSName(ss, i, ent);
|
|
if (acdbGetObjectId(id, ent) != Acad::eOk) continue;
|
|
AcDbObjectPointer<AecDbDimScaleZone> dsz(id, AcDb::kForRead);
|
|
if (dsz.openStatus() != Acad::eOk) continue;
|
|
if (dsz->PointInZone(pt))
|
|
arIds.append(id);
|
|
}
|
|
acedSSFree(ss);
|
|
acutRelRb(pRb);
|
|
|
|
if (arIds.isEmpty()) return false;
|
|
|
|
if (arIds.length() == 1)
|
|
{
|
|
AcDbObjectPointer<AecDbDimScaleZone> dsz(arIds.first(), AcDb::kForRead);
|
|
if (dsz.openStatus() != Acad::eOk) return false;
|
|
dScale = dsz->GetScale();
|
|
drawUnits = (AcDb::UnitsValue)dsz->GetDrawUnits();
|
|
dimUnits = (AcDb::UnitsValue)dsz->GetDimUnits();
|
|
return true;
|
|
}
|
|
|
|
// 分析多个情况
|
|
std::set<AecDbDimScaleZone*, COMPARE_ZONE_AREA> zones;
|
|
AcDbEntity *pEnt(NULL);
|
|
// 按照面积排序
|
|
for (int i(0); i < arIds.length(); ++i)
|
|
{
|
|
if (acdbOpenAcDbEntity(pEnt, arIds[i], AcDb::kForRead) != Acad::eOk) continue;
|
|
zones.insert((AecDbDimScaleZone*)pEnt);
|
|
}
|
|
|
|
// 如果面积最小的区域不在第二小的区域里,则存在区域交叉,不能判断
|
|
std::set<AecDbDimScaleZone*, COMPARE_ZONE_AREA>::const_iterator it(zones.begin())
|
|
, it1(zones.begin()), it2;
|
|
it2 = ++it;
|
|
|
|
bool bRel = (*it2)->RectInZone(**it1);
|
|
if (bRel)
|
|
{
|
|
dScale = (*it1)->GetScale();
|
|
drawUnits = (AcDb::UnitsValue)(*it1)->GetDrawUnits();
|
|
dimUnits = (AcDb::UnitsValue)(*it1)->GetDimUnits();
|
|
}
|
|
|
|
for (it = zones.begin(); it != zones.end(); ++it)
|
|
(*it)->close();
|
|
|
|
return bRel;
|
|
}
|