- UID
- 10108
- 积分
- 5956
- 精华
- 贡献
-
- 威望
-
- 活跃度
-
- D豆
-
- 在线时间
- 小时
- 注册时间
- 2002-9-17
- 最后登录
- 1970-1-1
|
马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有账号?立即注册
×
#include "stdafx.h"
#include "stdarx.h"
#include <MATH.H>
#include "GeUtilities.h"
#include "BrUtilities.h"
#include "CreateDbObj.h"
#include "DbUtilities.h"
void getPntsFromSpline(AcDbSpline *spl,AcGePoint3dArray& pnts)
{
int i,num;
if (spl->hasFitData()) {
num = spl->numFitPoints();
pnts.setLogicalLength(num);
for (i=0; i<num; i++) {
spl->getFitPointAt(i,pnts[i]);
}
} else {
int degree;
Adesk::Boolean bTmp;
AcGePoint3dArray tPnts;
AcGeDoubleArray weights,knots;
double dTmp,dTol;
spl->getNurbsData(degree,bTmp,bTmp,bTmp,tPnts,knots,weights,dTmp,dTol);
num = knots.length();
pnts.setLogicalLength(num);
int j = 0;
spl->getPointAtParam(knots[0],pnts[0]);
for (i=1; i<num; i++) {
if (fabs(knots[i]-knots[i-1]) > dTol) {
j++;
spl->getPointAtParam(knots[i],pnts[j]);
}
}
pnts.setLogicalLength(j+1);
}
}
void getPntsFromSpline(AcDbSpline *spl,AcGePoint3dArray& pnts,int pointnum)
{
int i,num;
if (spl->hasFitData()) {
num = spl->numFitPoints();
pnts.setLogicalLength(num);
for (i=0; i<num; i++) {
spl->getFitPointAt(i,pnts[i]);
}
} else {
int degree;
Adesk::Boolean bTmp;
AcGePoint3dArray tPnts;
AcGeDoubleArray weights,knots;
double dTmp,dTol;
spl->getNurbsData(degree,bTmp,bTmp,bTmp,tPnts,knots,weights,dTmp,dTol);
num = knots.length();
if (num<pointnum && pointnum>2) {
double minKnot,maxKnot,step;
minKnot = knots[0];
maxKnot = knots[num-1];
step = (maxKnot-minKnot)/(pointnum-1);
knots.setLogicalLength(pointnum);
num = pointnum;
knots[0] = minKnot;
for (i=1; i<num; i++) {
knots[i] = knots[i-1] + step;
}
}
pnts.setLogicalLength(num);
int j = 0;
spl->getPointAtParam(knots[0],pnts[0]);
for (i=1; i<num; i++) {
if (fabs(knots[i]-knots[i-1]) > dTol) {
j++;
spl->getPointAtParam(knots[i],pnts[j]);
}
}
pnts.setLogicalLength(j+1);
}
}
bool
getPntsFromCurve(AcDbCurve *pCurve,
AcGePoint3dArray& pnts,
int numPoint)
{
if ( numPoint<0
|| numPoint==1
|| !pCurve->isA()) return false;
pnts.setLogicalLength(0);
AcDbSpline *spl;
if (pCurve->getSpline(spl) == Acad::eOk) {
if (numPoint==0) {
getPntsFromSpline(spl,pnts);
} else {
getPntsFromSpline(spl,pnts,numPoint);
}
delete spl;
return true;
}
if (pCurve->isKindOf(AcDbLine::desc())) { // LINE
AcDbLine *pLine;
pLine = AcDbLine::cast(pCurve);
if (numPoint==0) {
pnts.append(pLine->startPoint());
pnts.append(pLine->endPoint());
} else {
double start,step;
AcGePoint3d pnt;
pLine->getStartParam(start);
pLine->getEndParam(step);
step = (step-start)/(numPoint-1);
for (register i=0; i<numPoint; i++) {
pLine->getPointAtParam(start,pnt);
pnts.append(pnt);
start = start + step;
}
}
return true;
}
if (pCurve->isKindOf(AcDbPolyline::desc())) { // LWPOLYLINE
AcDbPolyline *pPLine;
AcGePoint3d pnt;
pPLine = AcDbPolyline::cast(pCurve);
int len;
len = pPLine->numVerts();
for (register i=0; i<len; i++) {
pPLine->getPointAt(i,pnt);
pnts.append(pnt);
}
return true;
}
return false;
}
bool
getPntsFromCurve(AcGeCurve3d *pCurve,
AcGePoint3dArray& pnts,
int numPoint)
{
if ( numPoint<0
|| numPoint==1 ) return false;
pnts.setLogicalLength(0);
AcGe::EntityId type;
type = pCurve->type();
AcGeCurve3d *pNative;
bool bNative = false;
if (type == AcGe::kExternalCurve3d) {
if (((AcGeExternalCurve3d*)pCurve)->isNativeCurve(pNative)) {
bNative = true;
type = pNative->type();
} else {
return false;
}
} else {
pNative = pCurve;
}
switch(type) {
case AcGe::kLineSeg3d :
if (numPoint==0) {
pnts.setLogicalLength(2);
pNative->hasStartPoint(pnts[0]);
pNative->hasEndPoint(pnts[1]);
} else {
pNative->getSamplePoints(numPoint,pnts);
}
break;
case AcGe::kCircArc3d :
case AcGe::kEllipArc3d :
if (numPoint == 0) {
pNative->getSamplePoints(9,pnts);
} else {
pNative->getSamplePoints(numPoint,pnts);
}
break;
case AcGe::kNurbCurve3d :
getPntsFromSpline(*(AcGeNurbCurve3d*)pNative,pnts,numPoint);
break;
case AcGe::kPolyline3d :
AcGePolyline3d *pPoly;
pPoly = (AcGePolyline3d*)pNative;
int i,len;
len = pPoly->numControlPoints();
pnts.setLogicalLength(len);
for (i=0; i<len; i++) {
pnts[i] = pPoly->controlPointAt(i);
}
break;
default:
if (bNative) delete pNative;
return false;
}
if (bNative) delete pNative;
return true;
}
int minArr(const AcGeDoubleArray& arr)
{
int pos=0,i;
double min = arr[0];
for(i=1;i<arr.length();i++) {
if(arr[i]<min) {
min = arr[i];
pos = i;
}
}
return pos;
}
int maxArr(const AcGeDoubleArray& arr)
{
int pos=0,i;
double max = arr[0];
for(i=1;i<arr.length();i++) {
if(arr[i]>max) {
max = arr[i];
pos = i;
}
}
return pos;
}
int Round(const double& x)
{
if (x>0) {
return int(x+0.5f);
} else {
return int(x-0.5f);
}
}
double triangleArea(const AcGePoint2d& p1, const AcGePoint2d& p2, const AcGePoint2d& p3)
{
double area;
AcGeMatrix3d mat1;
mat1.setCoordSystem(AcGePoint3d(0.0f,0.0f,0.0f),AcGeVector3d(p1.x,p2.x,p3.x),
AcGeVector3d(p1.y,p2.y,p3.y),AcGeVector3d(1.0f,1.0f,1.0f));
area = mat1.det()/2.0;
return area;
}
double triangleArea(const AcGePoint3d& p1, const AcGePoint3d& p2, const AcGePoint3d& p3)
{
double area,a1,a2,a3;
AcGeMatrix3d mat1;
mat1.setCoordSystem(AcGePoint3d(0.0f,0.0f,0.0f),AcGeVector3d(p1.x,p2.x,p3.x),
AcGeVector3d(p1.y,p2.y,p3.y),AcGeVector3d(1.0f,1.0f,1.0f));
a1 = mat1.det();
mat1.setCoordSystem(AcGePoint3d(0.0f,0.0f,0.0f),AcGeVector3d(p1.y,p2.y,p3.y),
AcGeVector3d(p1.z,p2.z,p3.z),AcGeVector3d(1.0f,1.0f,1.0f));
a2 = mat1.det();
mat1.setCoordSystem(AcGePoint3d(0.0f,0.0f,0.0f),AcGeVector3d(p1.z,p2.z,p3.z),
AcGeVector3d(p1.x,p2.x,p3.x),AcGeVector3d(1.0f,1.0f,1.0f));
a3 = mat1.det();
area = sqrt(a1*a1+a2*a2+a3*a3)/2.0;
return area;
}
void reverse(ChGePnts2dArray& pntsArr)
{
int i,len;
len = pntsArr.length();
for (i=0; i<len; i++) {
pntsArr[i].reverse();
}
if (len>1) {
pntsArr.reverse();
}
}
void reverse(ChGePnts3dArray& pntsArr)
{
int i,len;
len = pntsArr.length();
for (i=0; i<len; i++) {
pntsArr[i].reverse();
}
if (len>1) {
pntsArr.reverse();
}
}
// 判断矢量vec1到vec2的方向是否为顺时针
Adesk::Boolean isClockwise(const AcGeVector2d& vec1, const AcGeVector2d& vec2)
{
AcGeVector3d vec3d1(vec1.x,vec1.y,0),vec3d2(vec2.x,vec2.y,0);
Adesk::Boolean bRet;
bRet = AcGeVector3d::kZAxis.isCodirectionalTo(
vec3d2.crossProduct(vec3d1));
return bRet;
}
// 判断点是否在直线的右手边
Adesk::Boolean isClockwise(const AcGeLine2d& line, const AcGePoint2d& pnt)
{
AcGePoint2d perpPnt;
AcGeLine2d perpLine,dirLine;
line.getPerpLine(pnt,perpLine);
line.intersectWith(perpLine,perpPnt);
dirLine.set(perpPnt,pnt);
return !perpLine.direction().isCodirectionalTo(dirLine.direction());
}
// 判断点是否在直线的右手边
Adesk::Boolean isClockwise(const AcGePoint2d& pnt,const AcGePoint2d& p1,const AcGePoint2d& p2)
{
AcGePoint2d perpPnt;
AcGeLine2d perpLine,dirLine;
AcGeLine2d line(p1,p2);
line.getPerpLine(pnt,perpLine);
line.intersectWith(perpLine,perpPnt);
dirLine.set(perpPnt,pnt);
return !perpLine.direction().isCodirectionalTo(dirLine.direction());
}
// 判断曲面上点相对曲线的方向,true右或false左
bool isClockwise(const AcGeNurbSurface& surf,const AcGePoint3dArray& curve,const AcGePoint3d& dirPnt)
{
// 参数平面上的点
AcGePoint2dArray curve2d;
AcGePoint2d dirPnt2d;
AcGePoint3d pnt;
int i,len;
len = curve.length();
if (!len) return false;
AcGePoint2d tParam2d;
for (i=0; i<len; i++) {
pnt = surf.closestPointTo(curve[i]);
surf.isOn(pnt,tParam2d);
curve2d.append(tParam2d);
}
pnt = surf.closestPointTo(dirPnt);
surf.isOn(pnt,dirPnt2d);
// dirPnt2d = surf.paramOf(pnt);
bool bDirRight = false;
AcGeNurbCurve2d spl(curve2d);
if (isClockwise(dirPnt2d,spl)) {
bDirRight = true;
}
return bDirRight;
}
// 由三点得到平面,当返回值Acad::eOk时返回的pln才有意义
Acad::ErrorStatus getPlaneFrom3Pnts(const AcGePoint3dArray& pnts,AcGePlane& pln)
{
if(pnts.length()!=3) return Acad::eInvalidInput;
AcGeVector3d vec1,vec2;
AcGePoint3d p1,p2,p;
vec1 = pnts[1]-pnts[0];
vec2 = pnts[2]-pnts[0];
vec1 = vec1.crossProduct(vec2);
pln.set(pnts[0],vec1);
pln.get(p1,p,p2);
if(p1.isEqualTo(AcGePoint3d(0.0f,0.0f,0.0f))) return Acad::eInvalidInput;
else return Acad::eOk;
}
// 由三点得到平面,当返回值Acad::eOk时返回的pln才有意义
Acad::ErrorStatus getPlaneFrom3Pnts(const AcGePoint3d& pp1, const AcGePoint3d& pp2,
const AcGePoint3d& pp3,AcGePlane& pln)
{
AcGePoint3dArray pnts;
pnts.append(pp1);
pnts.append(pp2);
pnts.append(pp3);
AcGeVector3d vec1,vec2;
AcGePoint3d p1,p2,p;
vec1 = pnts[1]-pnts[0];
vec2 = pnts[2]-pnts[0];
vec1 = vec1.crossProduct(vec2);
pln.set(pnts[0],vec1);
pln.get(p1,p,p2);
if(p1.isEqualTo(AcGePoint3d(0.0f,0.0f,0.0f))) return Acad::eInvalidInput;
else return Acad::eOk;
}
// 判断点相对于线段的位置,平面
int pointPosToLine(const AcGePoint2d& p,const AcGePoint2d& p1,const AcGePoint2d& p2)
{
AcGeVector2d vec1,vec2;
double angle;
if(p.isEqualTo(p1)) return 1; // 点与线段第一点重合
if(p.isEqualTo(p2)) return 2; // 点与线段第二点重合
vec1 = p1-p;
vec2 = p2-p;
angle = vec1.angleTo(vec2);
if(fabs(angle-PI)<TOL) return 0; // 点在线段上
else if(angle<TOL) return 3; // 点在线段延长线上
else return -1; // 点在线段外
}
// 判断点相对于线段的位置,空间
int pointPosToLine(const AcGePoint3d& p,const AcGePoint3d& p1,const AcGePoint3d& p2)
{
AcGeVector3d vec1,vec2;
double angle;
if(p.isEqualTo(p1)) return 1; // 点与线段第一点重合
if(p.isEqualTo(p2)) return 2; // 点与线段第二点重合
vec1 = p1-p;
vec2 = p2-p;
angle = vec1.angleTo(vec2);
if(fabs(angle-PI)<TOL) return 0; // 点在线段上
else if(fabs(angle)<TOL) return 3; // 点在线段延长线上
else return -1; // 点在线段外
}
// 判断点相对于三角形的位置
int pointPosToTriangle(const AcGePoint2d& pnt,AcGePoint2dArray& pnts)
{
int pos;
if (pnts.length()<3) return -1; // 不是三角形
if(pnt.isEqualTo(pnts[0])) return 1; // 点与三角形第一点重合
if(pnt.isEqualTo(pnts[1])) return 2; // 点与三角形第二点重合
if(pnt.isEqualTo(pnts[2])) return 3; // 点与三角形第三点重合
pos = pointPosToLine(pnt,pnts[0],pnts[1]);
if(pos==0) return 4;
else if(pos==3) return -1;
pos = pointPosToLine(pnt,pnts[1],pnts[2]);
if(pos==0) return 5;
else if(pos==3) return -1;
pos = pointPosToLine(pnt,pnts[2],pnts[0]);
if(pos==0) return 6;
else if(pos==3) return -1;
if(isClockwise(pnt,pnts[0],pnts[1])) return -1;
if(isClockwise(pnt,pnts[1],pnts[2])) return -1;
if(isClockwise(pnt,pnts[2],pnts[0])) return -1;
return 0;
}
// 由面积等比原则,通过三角形p1p2p3内一点p4,及对应得三角形r1r2r3,得出对应的点r4
bool mapPointInTriangle(AcGePoint2dArray& pnts1,AcGePoint2dArray& pnts2)
{
if (pnts1.length()!=4 || pnts2.length()!=4) return false;
double sigma[3],A,B,C,D,E,F,x,y;
sigma[0] = triangleArea(pnts1[0],pnts1[1],pnts1[3]);
sigma[1] = triangleArea(pnts1[1],pnts1[2],pnts1[3]);
sigma[2] = triangleArea(pnts1[2],pnts1[0],pnts1[3]);
A = (pnts2[1].y-pnts2[2].y)*sigma[2] - (pnts2[2].y-pnts2[0].y)*sigma[1];
B = (pnts2[1].x-pnts2[2].x)*sigma[2] - (pnts2[2].x-pnts2[0].x)*sigma[1];
C = (pnts2[1].x*pnts2[2].y-pnts2[2].x*pnts2[1].y)*sigma[2] -
(pnts2[2].x*pnts2[0].y-pnts2[0].x*pnts2[2].y)*sigma[1];
D = (pnts2[0].y-pnts2[1].y)*sigma[1] - (pnts2[1].y-pnts2[2].y)*sigma[0];
E = (pnts2[0].x-pnts2[1].x)*sigma[1] - (pnts2[1].x-pnts2[2].x)*sigma[0];
F = (pnts2[0].x*pnts2[1].y-pnts2[1].x*pnts2[0].y)*sigma[1] -
(pnts2[1].x*pnts2[2].y-pnts2[2].x*pnts2[1].y)*sigma[0];
x = (C*E-B*F)/(B*D-A*E);
y = (C*D-A*F)/(B*D-A*E);
pnts2[3].set(x,y);
return true;
}
// 由等比原则,通过, 线段p1p2内一点p3,及对应的线段r1r2,得出r1r2上对应的点r3
void mapPointInLine(AcGePoint2dArray& pnts1,AcGePoint2dArray& pnts2)
{
double sc;
sc = (pnts1[2]-pnts1[0]).length()/(pnts1[1]-pnts1[0]).length();
pnts2[2] = pnts2[0] + (pnts2[1]-pnts2[0])*sc;
}
// 由等比原则,通过, 线段p1p2内一点p3,及对应的线段r1r2,得出r1r2上对应的点r3
void mapPointInLine(AcGePoint3dArray& pnts1,AcGePoint2dArray& pnts2)
{
double sc;
sc = (pnts1[2]-pnts1[0]).length()/(pnts1[1]-pnts1[0]).length();
pnts2[2] = pnts2[0] + (pnts2[1]-pnts2[0])*sc;
}
// 由等比原则,通过, 线段p1p2内一点p3,及对应的线段r1r2,得出r1r2上对应的点r3
void mapPointInLine(AcGePoint2dArray& pnts1,AcGePoint3dArray& pnts2)
{
double sc;
sc = (pnts1[2]-pnts1[0]).length()/(pnts1[1]-pnts1[0]).length();
pnts2[2] = pnts2[0] + (pnts2[1]-pnts2[0])*sc;
}
bool mapPointTriangle(AcGePoint2dArray& pnts, AcGePoint2dArray& mpnts, bool bIfMapOut)
{
if (pnts.length()!=4 || mpnts.length()!=4) return false;
int pos;
pos = pointPosToTriangle(pnts[3],pnts);
if (pos>0) {
mapPointOnTriangle(pnts,pos,mpnts);
return true;
} else if (pos==0) {
mapPointInTriangle(pnts,mpnts);
return true;
} else {
if (bIfMapOut) {
mapPointInTriangle(pnts,mpnts);
}
}
return false;
}
// 三角形上(内,顶点,边),得出其映射点
bool mapPointOnTriangle(AcGePoint2dArray& pnts, int pos, AcGePoint2dArray& mpnts)
{
if (pos<1 || pos>6) return false;
if (pnts.length()!=4 || mpnts.length()!=4) return false;
AcGePoint2dArray line,mline;
line.setLogicalLength(3);
mline.setLogicalLength(3);
switch(pos) {
case 1:
mpnts[3] = mpnts[0];
break;
case 2:
mpnts[3] = mpnts[1];
break;
case 3:
mpnts[3] = mpnts[2];
break;
case 4:
line[0] = pnts[0];
line[1] = pnts[1];
line[2] = pnts[3];
mline[0] = mpnts[0];
mline[1] = mpnts[1];
mapPointInLine(line,mline);
mpnts[3] = mline[2];
break;
case 5:
line[0] = pnts[1];
line[1] = pnts[2];
line[2] = pnts[3];
mline[0] = mpnts[1];
mline[1] = mpnts[2];
mapPointInLine(line,mline);
mpnts[3] = mline[2];
break;
case 6:
line[0] = pnts[2];
line[1] = pnts[0];
line[2] = pnts[3];
mline[0] = mpnts[2];
mline[1] = mpnts[0];
mapPointInLine(line,mline);
mpnts[3] = mline[2];
break;
}
return true;
}
Adesk::Boolean isOnCurve(const AcGePoint2d& pnt, const AcGeNurbCurve2d& curve,const double& tol)
{
AcGePoint2d tmpp;
AcGeVector2dArray derivs;
AcGeVector2d vec;
tmpp = curve.closestPointTo(pnt);
if(tmpp.distanceTo(pnt)<tol) return true;
return false;
}
Adesk::Boolean isOnCurve(const AcGePoint2d& pnt, const AcGePolyline2d& ply,const double& tol)
{
double dist;
int i,len;
AcGeLineSeg2d line;
len = ply.numFitPoints();
for (i=0; i<len-1; i++) {
line.set(ply.fitPointAt(i),ply.fitPointAt(i+1));
dist = line.distanceTo(pnt);
if (dist < tol) return true;
}
return false;
}
Adesk::Boolean isClockwise(const AcGePoint2d& pnt, const AcGePolyline2d& ply)
{
AcGePoint2d closestPnt,tmpPnt;
AcGeVector2d vec,vec2,vec3;
double dist,min;
int i,len,minIndex;
AcGeLineSeg2d lineseg;
len = ply.numFitPoints();
closestPnt = ply.fitPointAt(0);
min = pnt.distanceTo(closestPnt);
minIndex = 0;
for (i=0; i<len-1; i++) {
lineseg.set(ply.fitPointAt(i),ply.fitPointAt(i+1));
tmpPnt = lineseg.closestPointTo(pnt);
dist = pnt.distanceTo(tmpPnt);
if (dist < min) {
minIndex = i;
min = dist;
closestPnt = tmpPnt;
}
}
vec = pnt - closestPnt;
if (len == 2) {
vec2 = ply.fitPointAt(1) - ply.fitPointAt(0);
return isClockwise(vec2,vec);
}
if (!closestPnt.isEqualTo(ply.fitPointAt(minIndex))
&& !closestPnt.isEqualTo(ply.fitPointAt(minIndex+1))) {
// 最近点不是顶点
vec2 = ply.fitPointAt(minIndex+1) - ply.fitPointAt(minIndex);
return isClockwise(vec2,vec);
}
if (closestPnt.isEqualTo(ply.fitPointAt(minIndex+1))) {
minIndex = minIndex + 1;
}
if ( minIndex == 0 || minIndex == len-1 ) {
if (ply.fitPointAt(0).isEqualTo(ply.fitPointAt(len-1))) {
vec2 = closestPnt - ply.fitPointAt(len-2);
vec3 = ply.fitPointAt(1) - closestPnt;
} else {
if (minIndex == 0) {
vec2 = ply.fitPointAt(1) - closestPnt;
} else {
vec2 = closestPnt - ply.fitPointAt(len-2);
}
return isClockwise(vec2,vec);
}
} else {
vec2 = ply.fitPointAt(minIndex) - ply.fitPointAt(minIndex-1);
vec3 = ply.fitPointAt(minIndex+1) - ply.fitPointAt(minIndex);
}
if (isClockwise(vec2,vec3)) {
if (isClockwise(vec2,vec) && isClockwise(vec3,vec)) {
return Adesk::kTrue;
} else {
return Adesk::kFalse;
}
} else {
if (isClockwise(vec2,vec) || isClockwise(vec3,vec)) {
return Adesk::kTrue;
} else {
return Adesk::kFalse;
}
}
}
Adesk::Boolean isClockwise(const AcGePoint2d& pnt, const AcGeNurbCurve2d& spl)
{
AcGePoint2d closedPnt;
double param;
AcGePointOnCurve2d pntOncrv;
AcGeVector2d vec,vec2,vec3;
spl.getClosestPointTo(pnt,pntOncrv);
param = pntOncrv.parameter();
closedPnt = pntOncrv.point();
vec = pnt-closedPnt;
if ( param == spl.startParam()
|| param == spl.endParam()) {
if (spl.startPoint().isEqualTo(spl.endPoint())) {
vec2 = pntOncrv.deriv(1,spl.endParam());
vec3 = pntOncrv.deriv(1,spl.startParam());
} else {
vec2 = pntOncrv.deriv(1);
return isClockwise(vec2,vec);
}
} else {
AcGeDoubleArray params;
spl.getParamsOfG1Discontinuity(params);
if (params.contains(param)) {
// 该点为方向矢量不连续点
vec3 = pntOncrv.deriv(1);
AcGeNurbCurve2d splCopy(spl);
splCopy.hardTrimByParams(splCopy.startParam(),param);
pntOncrv.setCurve(splCopy);
vec2 = pntOncrv.deriv(1,param);
} else {
vec2 = pntOncrv.deriv(1);
return isClockwise(vec2,vec);
}
}
if (isClockwise(vec2,vec3)) {
if (isClockwise(vec2,vec) && isClockwise(vec3,vec)) {
return Adesk::kTrue;
} else {
return Adesk::kFalse;
}
} else {
if (isClockwise(vec2,vec) || isClockwise(vec3,vec)) {
return Adesk::kTrue;
} else {
return Adesk::kFalse;
}
}
}
/*
// verify if point is on the right of curve
Adesk::Boolean isClockwise(const AcGePoint2d& pnt, const AcGeCurve2d& crv)
{
AcGePoint2d tmpp;
AcGeVector2d deriv;
AcGeVector2d vec;
AcGePointOnCurve2d pntOnCrv;
crv.getClosestPointTo(pnt,pntOnCrv);
tmpp = pntOnCrv.point();
double param1,len;
AcGeInterval intrvl;
crv.getInterval(intrvl);
param1 = pntOnCrv.parameter();
vec = pnt-tmpp;
len = crv.length(intrvl.lowerBound(),intrvl.upperBound())/1000;
double param2,param3;
if ( crv.length(param1,intrvl.upperBound()) < len
|| crv.length(intrvl.lowerBound(),param1) < len) {
// 最近点在曲线尾或头
if ( !crv.evalPoint(intrvl.lowerBound()).isEqualTo(
crv.evalPoint(intrvl.upperBound()))) {
deriv = pntOnCrv.deriv(1);
return isClockwise(deriv,vec);
} else {
param1 = intrvl.lowerBound();
param2 = crv.paramAtLength(intrvl.upperBound(),len,Adesk::kFalse);
param3 = crv.paramAtLength(param1,len);
}
} else {
param2 = crv.paramAtLength(param1,len,Adesk::kFalse);
param3 = crv.paramAtLength(param1,len);
}
AcGeVector2d vec2,vec3;
vec2 = tmpp - crv.evalPoint(param2);
vec3 = crv.evalPoint(param3) - tmpp;
if (isClockwise(vec2,vec3)) {
if (!isClockwise(vec2,vec) || !isClockwise(vec3,vec)) {
return Adesk::kFalse;
} else {
return Adesk::kTrue;
}
} else {
if (isClockwise(vec2,vec) || isClockwise(vec3,vec)) {
return Adesk::kTrue;
} else {
return Adesk::kFalse;
}
}
}
*/
Adesk::Boolean isCurveStartPoint(const AcGePoint2d& pnt, const AcGeCurve2d& curve,const double& tol)
{
AcGePoint2d stPoint;
curve.hasStartPoint(stPoint);
if(pnt.distanceTo(stPoint)<tol) return true;
return false;
}
Adesk::Boolean isCurveEndPoint(const AcGePoint2d& pnt, const AcGeCurve2d& curve,const double& tol)
{
AcGePoint2d edPoint;
curve.hasEndPoint(edPoint);
if(pnt.distanceTo(edPoint)<tol) return true;
return false;
}
int pointPosToExLoop(const AcGePoint2d& point,const ChGeLoop2d& loop,const double& tol)
{
int len=loop.length();
AcGeNurbCurve2d curve;
for(int i=0;i<len;i++) {
curve = AcGeNurbCurve2d(loop[i]);
if(isCurveStartPoint(point,curve,tol)) return (i+1);
}
for(i=0;i<len;i++) {
curve = AcGeNurbCurve2d(loop[i]);
if(isOnCurve(point,curve,tol)) return len+(i+1);
if(isClockwise(point,curve)) return -1;
}
return 0;
}
int pointPosToInLoop(const AcGePoint2d& point,const ChGeLoop2d& loop,const double& tol)
{
int len=loop.length();
AcGeNurbCurve2d curve;
for(int i=0;i<len;i++) {
curve = AcGeNurbCurve2d(loop[i]);
if(isCurveStartPoint(point,curve,tol)) return (i+1);
}
for(i=0;i<len;i++) {
curve = AcGeNurbCurve2d(loop[i]);
if(isOnCurve(point,curve,tol)) return len+(i+1);
if(!isClockwise(point,curve)) return -1;
}
return 0;
}
// 当param=param2=0时,表示全部段
bool getPntsFromSpline(const AcGeNurbCurve3d& curve,AcGePoint3dArray& pnts, const int& intNum,const double& param,const double& param2,const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 参数1是否大于参数2,缺省false
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
stP = curve.startParam();
edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) {
return false;
} else if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(stP)) return false;
if (!intrVal.contains(edP)) return false;
}
}
AcGeKnotVector cknots;
AcGeDoubleArray params;
int i,j,pos,pos2;
cknots = curve.knots();
cknots.getDistinctKnots(params);
pos = insertKnot(params,stP);
pos2 = insertKnot(params,edP);
AcGePoint3dArray dummy;
int startPos,endPos;
startPos = pos;
endPos = pos2;
double step,tmpVal;
for (i=startPos; i<endPos; i++) {
step = (params[i+1]-params[i])/(intNum+1);
tmpVal = params[i];
dummy.append(curve.evalPoint(tmpVal));
for (j=1; j<intNum+1; j++) {
tmpVal = tmpVal + step;
dummy.append(curve.evalPoint(tmpVal));
}
}
dummy.append(curve.evalPoint(params[endPos]));
if (bRev) {
dummy.reverse();
}
pnts = dummy;
return true;
}
// 当param=param2=0时,表示全部段
bool getPntsFromSpline(const AcGeNurbCurve2d& curve,AcGePoint2dArray& pnts, const int& intNum,const double& param,const double& param2,const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 是否参数1大于参数2,缺省false
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
stP = curve.startParam();
edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) return false;
if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(param)) return false;
if (!intrVal.contains(param2)) return false;
}
}
AcGeKnotVector cknots;
AcGeDoubleArray params;
int i,j,pos,pos2;
cknots = curve.knots();
cknots.getDistinctKnots(params);
pos = insertKnot(params,stP);
pos2 = insertKnot(params,edP);
AcGePoint2dArray dummy;
int startPos,endPos;
startPos = pos;
endPos = pos2;
double step,tmpVal;
for (i=startPos; i<endPos; i++) {
step = (params[i+1]-params[i])/(intNum+1);
tmpVal = params[i];
dummy.append(curve.evalPoint(tmpVal));
for (j=1; j<intNum+1; j++) {
tmpVal = tmpVal + step;
dummy.append(curve.evalPoint(tmpVal));
}
}
dummy.append(curve.evalPoint(params[endPos]));
if (bRev) {
dummy.reverse();
}
pnts = dummy;
return true;
}
bool getPntsFromSpline(AcGePoint2dArray& pnts,const AcGeNurbCurve2d& curve,const double& param,const double& param2,const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 是否参数1大于参数2,缺省false
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
stP = curve.startParam();
edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) return false;
if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(param)) return false;
if (!intrVal.contains(param2)) return false;
}
}
AcGeKnotVector cknots;
AcGeDoubleArray params;
int i,pos,pos2;
cknots = curve.knots();
cknots.getDistinctKnots(params);
pos = insertKnot(params,stP);
pos2 = insertKnot(params,edP);
AcGePoint2dArray dummy;
int startPos,endPos;
startPos = pos;
endPos = pos2;
for (i=startPos; i<endPos+1; i++) {
dummy.append(curve.evalPoint(params[i]));
}
if (bRev) {
dummy.reverse();
}
pnts = dummy;
return true;
}
bool getPntsFromSpline(AcGePoint3dArray& pnts,const AcGeNurbCurve3d& curve,const double& param,const double& param2,const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 是否参数1大于参数2,缺省false
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
stP = curve.startParam();
edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) return false;
if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(param)) return false;
if (!intrVal.contains(param2)) return false;
}
}
AcGeKnotVector cknots;
AcGeDoubleArray params;
int i,pos,pos2;
cknots = curve.knots();
cknots.getDistinctKnots(params);
pos = insertKnot(params,stP);
pos2 = insertKnot(params,edP);
AcGePoint3dArray dummy;
int startPos,endPos;
startPos = pos;
endPos = pos2;
for (i=startPos; i<endPos+1; i++) {
dummy.append(curve.evalPoint(params[i]));
}
if (bRev) {
dummy.reverse();
}
pnts = dummy;
return true;
}
bool isPartOfCurve(const AcGePoint3dArray& crv1,const AcGePoint3dArray& crv2, const double& tol)
{
if (!crv1.length() || !crv2.length()) return false;
double dist;
AcGeNurbCurve3d dummy(crv2);
int i,num;
num = crv1.length();
for (i=0; i<num; i++) {
dist = dummy.distanceTo(crv1[i]);
if (dist>tol) return false;
}
return true;
}
bool isPartOfCurve(const AcGePoint3dArray& crv1,const AcGeCurve3d& crv2, const double& tol)
{
double dist;
int i,num;
num = crv1.length();
if (num==0) return false;
for (i=0; i<num; i++) {
dist = crv2.distanceTo(crv1[i]);
if (dist>tol) return false;
}
return true;
}
bool isPartOfCurve(const AcGeNurbCurve3d& crv1,const AcGeCurve3d& crv2, const double& tol)
{
AcGePoint3dArray pnts1;
getPntsFromSpline(crv1,pnts1);
double dist;
int i,num;
num = pnts1.length();
if (num==0) return false;
for (i=0; i<num; i++) {
dist = crv2.distanceTo(pnts1[i]);
if (dist>tol) return false;
}
return true;
}
bool isPartOfCurve(const AcGePoint2dArray& crv1,const AcGePoint2dArray& crv2, const double& tol)
{
if (!crv1.length() || !crv2.length()) return false;
double dist;
AcGeNurbCurve2d dummy(crv2);
int i,num;
num = crv1.length();
for (i=0; i<num; i++) {
dist = dummy.distanceTo(crv1[i]);
if (dist>tol) return false;
}
return true;
}
bool isPartOfCurve(const AcGePoint2dArray& crv1,const AcGeCurve2d& crv2, const double& tol)
{
double dist;
int i,num;
num = crv1.length();
if (num==0) return false;
for (i=0; i<num; i++) {
dist = crv2.distanceTo(crv1[i]);
if (dist>tol) return false;
}
return true;
}
bool isPartOfCurve(const AcGeNurbCurve2d& crv1,const AcGeCurve2d& crv2, const double& tol)
{
AcGePoint2dArray pnts1;
getPntsFromSpline(crv1,pnts1);
double dist;
int i,num;
num = pnts1.length();
if (num==0) return false;
for (i=0; i<num; i++) {
dist = crv2.distanceTo(pnts1[i]);
if (dist>tol) return false;
}
return true;
}
// 在节点数组中添加节点参数,形成新的节点数组,从小到大的顺序,返回其在新节点数组中的位置
int insertKnot(AcGeDoubleArray& knots,const double& val)
{
int i,len;
if (knots.find(val,i)) return i;
len = knots.length();
for (i=0; i<len; i++) {
if (val < knots[i]) {
knots.insertAt(i,val);
return i;
}
}
knots.insertAt(i,val);
return i;
}
void getJoinedCurveFromPntsArray(const ChGeCurve2dPntsArray& curves, AcGeNurbCurve2d& curve)
{
AcGePoint2dArray pnts;
AcGeNurbCurve2d tmpCrv;
int i,len;
len = curves.length();
if (len) {
curve = AcGeNurbCurve2d(curves[0]);
}
for (i=1; i<len; i++) {
tmpCrv = AcGeNurbCurve2d(curves[i]);
curve.joinWith(tmpCrv);
}
}
void getJoinedCurveFromPntsArray(const ChGeCurve3dPntsArray& curves, AcGeNurbCurve3d& curve)
{
AcGePoint3dArray pnts;
AcGeNurbCurve3d tmpCrv;
int i,len;
len = curves.length();
if (len) {
curve = AcGeNurbCurve3d(curves[0]);
}
for (i=1; i<len; i++) {
tmpCrv = AcGeNurbCurve3d(curves[i]);
curve.joinWith(tmpCrv);
}
}
void getPolylineFromPntsArray(const ChGeCurve2dPntsArray& curves, AcGePolyline2d& curve)
{
AcGePoint2dArray pnts;
int i,len;
len = curves.length();
if (len>0) {
pnts.append(curves.first());
}
for (i=1; i<len; i++) {
pnts.removeLast();
pnts.append(curves[i]);
}
curve = AcGePolyline2d(pnts);
}
void getPolylineFromPntsArray(const ChGeCurve3dPntsArray& curves, AcGePolyline3d& curve)
{
AcGePoint3dArray pnts;
int i,len;
len = curves.length();
if (len>0) {
pnts.append(curves.first());
}
for (i=1; i<len; i++) {
pnts.removeLast();
pnts.append(curves[i]);
}
curve = AcGePolyline3d(pnts);
}
bool getPntsArrayFromJoinedCurve(const AcGeNurbCurve2d& curve,
ChGeCurve2dPntsArray& curves,
const int& intNum,
const double& param,
const double& param2,
const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 是否参数1大于参数2,缺省false
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
stP = curve.startParam();
edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) return false;
if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(param)) return false;
if (!intrVal.contains(param2)) return false;
}
}
AcGePoint2dArray pnts;
AcGeDoubleArray params;
curve.getParamsOfC1Discontinuity(params);
curves.setLogicalLength(0);
if (!bExt) {
insertKnot(params,curve.startParam());
insertKnot(params,curve.endParam());
}
int pos;
pos = insertKnot(params,stP);
if (pos>0) {
params.removeSubArray(0,pos-1);
}
pos = insertKnot(params,edP);
if (pos<params.length()-1) {
params.removeSubArray(pos+1,params.length()-1);
}
int i,len;
len = params.length();
for (i=0; i+1<len; i++) {
pnts.setLogicalLength(0);
getPntsFromSpline(curve,pnts,intNum,params[i],params[i+1],bExt);
if (pnts.length()) {
if (bRev) pnts.reverse();
curves.append(pnts);
}
}
if (bRev) curves.reverse();
return true;
}
bool getPntsArrayFromJoinedCurve(ChGeCurve2dPntsArray& curves,
const AcGeNurbCurve2d& curve,
const double& param,
const double& param2,
const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 是否参数1大于参数2,缺省false
curves.setLogicalLength(0);
/*
AcGe::EntityId entId;
if (curve.isDegenerate(entId)) {
if (entId == AcGe::kPointEnt2d) {
return false;
}
}
*/
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
AcGeInterval intrvl;
curve.getInterval(intrvl);
stP = intrvl.lowerBound();
edP = intrvl.upperBound();
// stP = curve.startParam();
// edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) return false;
if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(param)) return false;
if (!intrVal.contains(param2)) return false;
}
}
AcGePoint2dArray pnts;
AcGeDoubleArray params;
curve.getParamsOfC1Discontinuity(params);
curves.setLogicalLength(0);
if (!bExt) {
insertKnot(params,curve.startParam());
insertKnot(params,curve.endParam());
}
int pos;
pos = insertKnot(params,stP);
if (pos>0) {
params.removeSubArray(0,pos-1);
}
pos = insertKnot(params,edP);
if (pos<params.length()-1) {
params.removeSubArray(pos+1,params.length()-1);
}
int i,len;
len = params.length();
for (i=0; i+1<len; i++) {
pnts.setLogicalLength(0);
getPntsFromSpline(pnts,curve,params[i],params[i+1],bExt);
if (pnts.length()) {
if (bRev) pnts.reverse();
curves.append(pnts);
}
}
if (bRev) curves.reverse();
return true;
}
bool getPntsArrayFromJoinedCurve(ChGeCurve3dPntsArray& curves,
const AcGeNurbCurve3d& curve,
const double& param,
const double& param2,
const bool& bExt)
{
double tol = AcGeContext::gTol.equalPoint();
double stP,edP;
bool bRev = false; // 是否参数1大于参数2,缺省false
curves.setLogicalLength(0);
/*
AcGe::EntityId entId;
if (curve.isDegenerate(entId)) {
if (entId == AcGe::kPointEnt3d) {
return false;
}
}
*/
if (fabs(param-param2)<=tol && fabs(param2)<=tol) {
AcGeInterval intrvl;
curve.getInterval(intrvl);
stP = intrvl.lowerBound();
edP = intrvl.upperBound();
// stP = curve.startParam();
// edP = curve.endParam();
} else {
if (fabs(param-param2)<=tol) return false;
if (param > param2) {
bRev = true;
stP = param2;
edP = param;
} else {
bRev = false;
stP = param;
edP = param2;
}
if (!bExt) {
AcGeInterval intrVal;
curve.getInterval(intrVal);
if (!intrVal.contains(param)) return false;
if (!intrVal.contains(param2)) return false;
}
}
AcGePoint3dArray pnts;
AcGeDoubleArray params;
curve.getParamsOfC1Discontinuity(params);
curves.setLogicalLength(0);
if (!bExt) {
insertKnot(params,curve.startParam());
insertKnot(params,curve.endParam());
}
int pos;
pos = insertKnot(params,stP);
if (pos>0) {
params.removeSubArray(0,pos-1);
}
pos = insertKnot(params,edP);
if (pos<params.length()-1) {
params.removeSubArray(pos+1,params.length()-1);
}
int i,len;
len = params.length();
for (i=0; i+1<len; i++) {
pnts.setLogicalLength(0);
getPntsFromSpline(pnts,curve,params[i],params[i+1],bExt);
if (pnts.length()) {
if (bRev) pnts.reverse();
curves.append(pnts);
}
}
if (bRev) curves.reverse();
return true;
}
// 转换3d点数组为2d点数组
void points3dTo2d(const AcGePoint3dArray& pnts3d,AcGePoint2dArray& pnts2d)
{
int i,len;
len = pnts3d.length();
pnts2d.setLogicalLength(len);
for (i=0; i<len; i++) {
pnts2d[i] = AcGePoint2d(pnts3d[i].x,pnts3d[i].y);
}
}
// 转换2d点数组为3d点数组
void points2dTo3d(const AcGePoint2dArray& pnts2d,AcGePoint3dArray& pnts3d,const double& z)
{
int i,len;
len = pnts2d.length();
pnts3d.setLogicalLength(len);
for (i=0; i<len; i++) {
pnts3d[i] = AcGePoint3d(pnts2d[i].x,pnts2d[i].y,z);
}
}
void curve3dTo2d(const AcGeNurbCurve3d& crv,AcGeNurbCurve2d& crv2d)
{
int degree;
Adesk::Boolean rational,periodic;
AcGeKnotVector knots;
AcGePoint3dArray controlPoints;
AcGePoint2dArray controlPoints2d;
AcGeDoubleArray weights;
crv.getDefinitionData(degree,rational,periodic,knots,controlPoints,weights);
points3dTo2d(controlPoints,controlPoints2d);
crv2d = AcGeNurbCurve2d(degree,knots,controlPoints2d,weights,periodic);
}
int joinPntsArrayWithPnts(ChGePnts2dArray& pntsArr, const AcGePoint2dArray& pnts)
{
int pos = -1;
for (int j=0,LenArr=pntsArr.length(); j<LenArr; j++) {
if (pnts.first().isEqualTo(pntsArr[j].last())) {
pos = j+1;
break;
}
}
if (pos != -1) {
pntsArr.insertAt(pos,pnts);
}
return pos;
}
int joinPntsArrayWithPntsArray(ChGePnts2dArray& pntsArr, const ChGePnts2dArray& pntsArr2)
{
AcGePoint2d fp,lp;
int pos = -1;
fp = pntsArr2.first().first();
lp = pntsArr2.last().last();
bool bRev=false;
int j,LenArr;
LenArr = pntsArr.length();
for (j=0; j<LenArr; j++) {
if (fp.isEqualTo(pntsArr[j].last())) {
pos = j+1;
break;
}
if (lp.isEqualTo(pntsArr[j].last())) {
bRev = true;
pos = j+1;
break;
}
}
if (pos != -1) {
LenArr = pntsArr2.length();
if (!bRev) {
for (j=LenArr-1; j>-1; j--) {
pntsArr.insertAt(pos,pntsArr2[j]);
}
} else {
for (j=0; j<LenArr; j++) {
pntsArr.insertAt(pos,pntsArr2[j]);
pntsArr[pos].reverse();
}
}
}
return pos;
}
void Loop2dTo3d(const ChGeLoop2d& loop2d, ChGeLoop3d& loop3d, double z)
{
int i,len;
len = loop2d.length();
loop3d.setLogicalLength(len);
for (i=0; i<len; i++) {
points2dTo3d(loop2d[i],loop3d[i],z);
}
}
void Loop3dTo2d(const ChGeLoop3d& loop3d, ChGeLoop2d& loop2d)
{
int i,len;
len = loop3d.length();
loop2d.setLogicalLength(len);
for (i=0; i<len; i++) {
points3dTo2d(loop3d[i],loop2d[i]);
}
}
void Loops2dTo3d(const ChGeLoop2dArray& loops2d,
ChGeLoop3dArray& loops3d, double z)
{
int i,len;
len = loops2d.length();
loops3d.setLogicalLength(len);
for (i=0; i<len; i++) {
Loop2dTo3d(loops2d[i],loops3d[i],z);
}
}
void Loops3dTo2d(const ChGeLoop3dArray& loops3d,
ChGeLoop2dArray& loops2d)
{
int i,len;
len = loops3d.length();
loops2d.setLogicalLength(len);
for (i=0; i<len; i++) {
Loop3dTo2d(loops3d[i],loops2d[i]);
}
}
// 整理Loop, 去掉数组中前后相等的点, 去掉点数为1的数组,
// 如果最终不能形成loop则返回kFalse
Adesk::Boolean regenLoop(ChGeLoop2d& loop)
{
if (loop.isEmpty()) return Adesk::kFalse;
if (!loop.first().first().isEqualTo(loop.last().last())) return false;
int i,len,j,jlen;
len = loop.length();
for (i=0; i<len; i++) {
jlen = loop[i].length();
for (j=jlen-1; j>0; j--) {
if (loop[i].at(j).isEqualTo(loop[i].at(j-1))) {
loop[i].removeAt(j);
}
}
}
for (i=0; i<len-1; i++) {
if (!loop[i].last().isEqualTo(loop[i+1].first())) {
return Adesk::kFalse;
}
}
return Adesk::kTrue;
}
Acad::ErrorStatus
getLoopsFromRegion(AcDbRegion *pRg, ChGeLoop3dArray& loops)
{
short marker;
AcGePoint3d pickpnt;
AcGeMatrix3d vxform;
int numIds;
AcDbFullSubentPath *subentIds;
AcDbFullSubentPathArray subentIdArr;
AcBrFace *pBrFace;
AcBrLoopPointerArray pBrLoops;
loops.setLogicalLength(0);
marker = 0;
do {
marker++;
pRg->getSubentPathsAtGsMarker(AcDb::kFaceSubentType,marker,
pickpnt,vxform,numIds,subentIds);
if (numIds==0) break;
for (register j=0; j<numIds; j++) {
if ( !subentIdArr.contains(subentIds[j]) ) {
subentIdArr.append(subentIds[j]);
}
}
delete [] subentIds;
} while(true);
numIds = subentIdArr.length();
if (numIds==0) return Acad::eWrongObjectType;
int i;
ChGeLoop3dArray retLoops;
for (i=0; i<numIds; i++) {
pBrFace = new AcBrFace;
pBrFace->setSubentPath(subentIdArr[i]);
getBrLoopsFromBrFace(pBrFace,pBrLoops);
getGeLoopsFromBrLoops(pBrLoops,retLoops);
loops.append(retLoops);
int j,jlen;
jlen = pBrLoops.length();
for (j=0; j<jlen; j++) {
delete (AcBrLoop*)(pBrLoops[j]);
}
pBrLoops.setLogicalLength(0);
retLoops.setLogicalLength(0);
delete pBrFace;
}
int len;
len = loops.length();
for (i=0; i<len; i++) {
int j,jlen,klen;
jlen = loops[i].length();
for (j=jlen-1; j>-1; j--) {
klen = loops[i].at(j).length();
if (klen<2) loops[i].removeAt(j);
}
}
return Acad::eOk;
}
Acad::ErrorStatus
booleanOper(const ChGeLoop2d& loop1, const ChGeLoop2d& loop2,
ChGeLoop2dArray& retLoops,AcDb::BoolOperType op)
{
AcDbRegion *pRg1,*pRg2;
Acad::ErrorStatus es;
es = createRegion(loop1,pRg1);
if (es != Acad::eOk) return es;
es = createRegion(loop2,pRg2);
if (es != Acad::eOk) {
delete pRg1;
return es;
}
AcGePoint3dArray pnts3d;
pRg1->intersectWith(pRg2,AcDb::kOnBothOperands,pnts3d,0,0);
es = pRg1->booleanOper(op,pRg2);
if (es != Acad::eOk) return es;
acdbHostApplicationServices()->workingDatabase()->
addAcDbObject(pRg1);
ChGeLoop3dArray loops;
es = getLoopsFromRegion(pRg1,loops);
pRg1->erase ();
pRg1->close();
if (es != Acad::eOk) return es;
Loops3dTo2d(loops,retLoops);
if (retLoops.length() == 1) {
if ( (retLoops[0].length()==loop1.length())
&& pnts3d.length()==0 ) {
return Acad::eNotHandled;
}
}
return Acad::eOk;
}
Acad::ErrorStatus
trimLoopByCurve(const ChGeLoop2d& loop,const ChGePnts2dArray& curve,
ChGeLoop2d& retLoop, Adesk::Boolean bTrimRight, Adesk::Boolean bAntiClock)
{
retLoop.setLogicalLength(0);
Acad::ErrorStatus es;
ChGePnts2dArray retCurve;
es = trimCurveByLoop(curve,loop,retCurve);
if (es != Acad::eOk) {
return es;
}
AcGeNurbCurve2d loopCrv;
getJoinedCurveFromPntsArray(loop,loopCrv);
double param1,param2;
loopCrv.isOn(retCurve.first().first(),param1);
loopCrv.isOn(retCurve.last().last(),param2);
retCurve.first().first() = loopCrv.evalPoint(param1);
retCurve.last().last() = loopCrv.evalPoint(param2);
ChGePnts2dArray retPntsArray;
if (bAntiClock) {
if (bTrimRight) {
if (param1<param2) {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,loopCrv.startParam(),param1);
retLoop.append(retPntsArray);
retLoop.append(retCurve);
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param2,loopCrv.endParam());
retLoop.append(retPntsArray);
} else {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param2,param1);
retLoop.append(retPntsArray);
retLoop.append(retCurve);
}
} else {
if (param1<param2) {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param1,param2);
retLoop.append(retPntsArray);
reverse(retCurve);
retLoop.append(retCurve);
} else {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,loopCrv.startParam(),param2);
retLoop.append(retPntsArray);
reverse(retCurve);
retLoop.append(retCurve);
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param1,loopCrv.endParam());
retLoop.append(retPntsArray);
}
}
} else {
if (bTrimRight) {
if (param1<param2) {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param1,param2);
retLoop.append(retPntsArray);
reverse(retCurve);
retLoop.append(retCurve);
} else {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,loopCrv.startParam(),param2);
retLoop.append(retPntsArray);
reverse(retCurve);
retLoop.append(retCurve);
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param1,loopCrv.endParam());
retLoop.append(retPntsArray);
}
} else {
if (param1<param2) {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,loopCrv.startParam(),param1);
retLoop.append(retPntsArray);
retLoop.append(retCurve);
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param2,loopCrv.endParam());
retLoop.append(retPntsArray);
} else {
getPntsArrayFromJoinedCurve(retPntsArray,loopCrv,param2,param1);
retLoop.append(retPntsArray);
retLoop.append(retCurve);
}
}
}
return Acad::eOk;
}
Acad::ErrorStatus
trimCurveByLoop(const ChGePnts2dArray& curve,const ChGeLoop2d& loop,
ChGePnts2dArray& retCurve)
{
retCurve.setLogicalLength(0);
Acad::ErrorStatus es;
AcDbRegion *pRg;
es = createRegion(loop,pRg);
if (es != Acad::eOk)
return es;
AcGeNurbCurve2d crv;
getJoinedCurveFromPntsArray(curve,crv);
AcDbSpline *pSpl;
createSpline(crv,pSpl);
AcGePoint3dArray pnts3d;
pRg->intersectWith(pSpl,AcDb::kOnBothOperands,pnts3d,0,0);
delete pSpl;
int len;
len = pnts3d.length(); // 交点个数
if ( len > 2) {
delete pRg;
return Acad::eNotHandled;
}
double param1,param2;
acdbHostApplicationServices()->workingDatabase()->
addAcDbObject(pRg);
AcBrFace *pBrFace;
getBrFaceFromRegion(pRg,pBrFace);
AcBr::Relation rel;
AcGePoint2d pnt2d;
if (len==0) {
double tol;
AcGeNurbCurve2d loopCrv;
getJoinedCurveFromPntsArray(loop,loopCrv);
pnt2d = crv.evalPoint(crv.endParam()/2);
pBrFace->getPointRelationToFace(AcGePoint3d(pnt2d.x,pnt2d.y,0),rel);
if (rel == AcBr::kInside) {
retCurve = curve;
} else {
tol = loopCrv.distanceTo(pnt2d);
if (tol < TOL5) {
retCurve = curve;
}
}
pRg->erase();
pRg->close();
delete pBrFace;
return Acad::eNotHandled;
}
if (len==1) {
pnt2d = curve.first().first();
pBrFace->getPointRelationToFace(AcGePoint3d(pnt2d.x,pnt2d.y,0),rel);
if (rel == AcBr::kInside) {
param1 = crv.startParam();
crv.isOn(AcGePoint2d(pnts3d[0].x,pnts3d[0].y),param2);
} else {
crv.isOn(AcGePoint2d(pnts3d[0].x,pnts3d[0].y),param1);
param2 = crv.endParam();
}
if (param1 == param2) {
// 全部被剪切
pRg->erase();
pRg->close();
delete pBrFace;
return Acad::eOk;
}
} else if (len==2) {
crv.isOn(AcGePoint2d(pnts3d[0].x,pnts3d[0].y),param1);
crv.isOn(AcGePoint2d(pnts3d[1].x,pnts3d[1].y),param2);
pnt2d = crv.evalPoint((param1+param2)/2);
pBrFace->getPointRelationToFace(AcGePoint3d(pnt2d.x,pnt2d.y,0),rel);
if (rel != AcBr::kInside) {
pRg->erase();
pRg->close();
delete pBrFace;
return Acad::eNotHandled;
}
if (param1>param2) {
double tmp;
tmp = param1;
param1 = param2;
param2 = tmp;
}
}
pRg->erase();
pRg->close();
delete pBrFace;
getPntsArrayFromJoinedCurve(retCurve,crv,param1,param2);
return Acad::eOk;
}
/*
bool trimLoopByLoops(const ChGeLoop2d& loop, const ChGeLoop2dArray& loops,ChGeLoop2dArray& retLoops,bool bAnticlock,bool bTrimRight)
{
if (loop.length()==0 || loops.length()==0) return false;
retLoops.setLogicalLength(0);
bool ret;
ChGePnts2dArray retPntsArr;
ChGeLoop2dArray trimmedLoops,trimmedLoops2,innerLoops,tmpLoops;
int i,len,j,jlen;
len = loops.length();
trimmedLoops.append(loop);
for (i=0; i<len; i++) {
jlen = trimmedLoops.length();
trimmedLoops2.setLogicalLength(0);
for (j=0; j<jlen; j++) {
ret = trimClosedCurvebyClosedCurve(
trimmedLoops[j],loops[i],retPntsArr,bTrimRight,bAnticlock);
if (ret) {
if (retPntsArr.length()!=0) {
// 部分被剪切
getLoopsFromPntsArr(tmpLoops,retPntsArr);
trimmedLoops2.append(tmpLoops);
}
} else {
if (retPntsArr.length() == trimmedLoops[j].length()) {
// 未被剪切
AcGeNurbCurve2d crv;
getJoinedCurveFromPntsArray(trimmedLoops[j],crv);
Adesk::Boolean bTmp;
bTmp = isClockwise(loops[i].first().first(),crv);
if (bAnticlock) {
if (!bTmp) {
innerLoops.append(loops[i]);
}
} else {
if (bTmp) {
innerLoops.append(loops[i]);
}
}
trimmedLoops2.append(trimmedLoops[j]);
} else {
// 输入参数错误
return false;
}
}
}
trimmedLoops = trimmedLoops2;
if (trimmedLoops.length()==0) {
return true;
}
}
retLoops = trimmedLoops;
if (innerLoops.length()) {
retLoops.append(innerLoops);
}
return true;
}
*/
// 从点数组的数组提取loops
bool getLoopsFromPntsArr(ChGeLoop2dArray& loops2d,const ChGeCurve2dPntsArray& pntsArr)
{
int i,len;
len = pntsArr.length();
loops2d.setLogicalLength(0);
if (len==0) {
return false;
} else if (len==1) {
if (pntsArr[0].length()>1 && pntsArr[0].first().isEqualTo(pntsArr[0].last())) {
loops2d.append(pntsArr);
return true;
} else {
return false;
}
} else {
ChGeLoop2d loop;
loop.append(pntsArr[0]);
for (i=1; i<len; i++) {
while(pntsArr[i-1].last().isEqualTo(pntsArr[i].first())) {
loop.append(pntsArr[i]);
i++;
if (i>=len) break;
}
if (loop.length()) loops2d.append(loop);
loop.setLogicalLength(0);
if (i!=len) {
loop.append(pntsArr[i]);
}
}
if (loop.length()) {
loops2d.append(loop);
}
if (loops2d.length()>1) {
if (loops2d.first().first().first().isEqualTo(loops2d.last().last().last())) {
loops2d[loops2d.length()].append(loops2d.first());
// loops2d.last().append(loops2d.first());
loops2d.removeFirst();
}
}
}
len = loops2d.length();
for (i=len-1; i>-1; i--) {
if (!loops2d[i].first().first().isEqualTo(loops2d[i].last().last())) {
loops2d.removeAt(i);
}
}
if (loops2d.length()) return true;
else return false;
}
bool isEqual(const ChGeLoop2d& loop1,const ChGeLoop2d& loop2)
{
int i,len;
len = loop1.length();
if (loop2.length() != len) return false;
for (i=0; i<len; i++) {
if (!isEqual(loop1[i],loop2[i])) return false;
}
return true;
}
bool isEqual(const AcGePoint2dArray& pnts1,const AcGePoint2dArray& pnts2)
{
int i,len;
len = pnts1.length();
if (pnts2.length() != len) return false;
for (i=0; i<len; i++) {
if (!pnts1[i].isEqualTo(pnts2[i])) return false;
}
return true;
}
bool isEqual(const ChGeLoop2dArray& loops1,const ChGeLoop2dArray& loops2)
{
int i,len;
len = loops1.length();
if (loops2.length() != len) return false;
for (i=0; i<len; i++) {
if (!isEqual(loops1[i],loops2[i])) return false;
}
return true;
}
bool getParamsFromPnts(const AcGeNurbSurface& surf,const AcGePoint3dArray& pnts,AcGePoint2dArray& params)
{
if (!pnts.length()) return false;
int i,len;
len = pnts.length();
AcGePoint3dArray tmpPnts;
tmpPnts.append(pnts.first());
for (i=1; i<len; i++) {
if (!tmpPnts.last().isEqualTo(pnts[i])) {
tmpPnts.append(pnts[i]);
}
}
len = tmpPnts.length();
params.setLogicalLength(len);
AcGePoint3d pnt3d;
for (i=0; i<len; i++) {
pnt3d = surf.closestPointTo(tmpPnts[i]);
surf.isOn(pnt3d,params[i]);
// params[i] = surf.paramOf(pnt3d);
}
if (len>2) {
// 判断曲面的奇异性,是否有边退化为点
AcGeInterval intrvlX,intrvlY;
surf.getEnvelope(intrvlX,intrvlY);
int nSigularity=0;
AcGePoint3d p1,p2,p3,p4,oSigularity;
AcGePoint2d param;
p1 = surf.evalPoint(param.set(intrvlX.lowerBound(),intrvlY.lowerBound()));
p2 = surf.evalPoint(param.set(intrvlX.upperBound(),intrvlY.lowerBound()));
p3 = surf.evalPoint(param.set(intrvlX.upperBound(),intrvlY.upperBound()));
p4 = surf.evalPoint(param.set(intrvlX.lowerBound(),intrvlY.upperBound()));
if (p1.isEqualTo(p2)) {
nSigularity = 1;
oSigularity = p1;
} else if (p2.isEqualTo(p3)) {
nSigularity = 2;
oSigularity = p2;
} else if (p3.isEqualTo(p4)) {
nSigularity = 3;
oSigularity = p3;
} else if (p4.isEqualTo(p1)) {
nSigularity = 4;
oSigularity = p4;
}
if (nSigularity) {
AcGeLine2d l2;
AcGeLineSeg2d l1;
AcGePoint2d tp1,tp2;
switch(nSigularity) {
case 1:
tp1.set(intrvlX.lowerBound(),intrvlY.lowerBound());
tp2.set(intrvlX.upperBound(),intrvlY.lowerBound());
l1.set(tp1,tp2);
break;
case 2:
tp1.set(intrvlX.upperBound(),intrvlY.lowerBound());
tp2.set(intrvlX.upperBound(),intrvlY.upperBound());
l1.set(tp1,tp2);
break;
case 3:
tp1.set(intrvlX.upperBound(),intrvlY.upperBound());
tp2.set(intrvlX.lowerBound(),intrvlY.upperBound());
l1.set(tp1,tp2);
break;
case 4:
tp1.set(intrvlX.lowerBound(),intrvlY.upperBound());
tp2.set(intrvlX.lowerBound(),intrvlY.lowerBound());
l1.set(tp1,tp2);
break;
}
// 针对数组的首位进行判断
if (tmpPnts.first().isEqualTo(oSigularity)) {
l2.set(params.at(1),params.at(2));
if (!l1.intersectWith(l2,params.first())) {
double s1;
s1 = (tmpPnts[0]-tmpPnts[1]).length() / (tmpPnts[1]-tmpPnts[2]).length();
params[0] = params[1] + (params[1]-params[2])*s1;
params[0] = l1.closestPointTo(params[0]);
}
}
// 针对数组的第二位进行判断
if (tmpPnts.at(1).isEqualTo(oSigularity)) {
l2.set(params.at(0),params.at(2));
if (!l1.intersectWith(l2,params[1])) {
double s1;
s1 = (tmpPnts[1]-tmpPnts[0]).length() / (tmpPnts[2]-tmpPnts[0]).length();
params[1] = params[0] + (params[2]-params[0])*s1;
params[1] = l1.closestPointTo(params[1]);
}
}
// 针对其他
for (i=2; i<len; i++) {
if (tmpPnts.at(i).isEqualTo(oSigularity)) {
l2.set(params.at(i-1),params.at(i-2));
if (!l1.intersectWith(l2,params.first())) {
double s1;
s1 = (tmpPnts[i-1]-tmpPnts[i-2]).length() / (tmpPnts[i-1]-tmpPnts[i-2]).length();
params[i] = params[i-1] + (params[i-1]-params[i-2])*s1;
params[i] = l1.closestPointTo(params[i]);
}
}
}
}
}
return true;
}
bool getPntsFromParams(const AcGeNurbSurface& surf,const AcGePoint2dArray& params,AcGePoint3dArray& pnts)
{
if (!params.length()) return false;
int i,len;
len = params.length();
pnts.setLogicalLength(len);
for (i=0; i<len; i++) {
pnts[i] = surf.evalPoint(params[i]);
}
return true;
}
bool getParamsArrayFromPntsArray(const AcGeNurbSurface& surf,const ChGePnts3dArray& pntsArr,ChGePnts2dArray& paramsArr, bool bLoop)
{
if (!pntsArr.length()) return false;
int i,len,j,jlen;
AcGePoint2d param;
len = pntsArr.length();
paramsArr.setLogicalLength(len);
AcGePoint3d pnt3d;
for (i=0; i<len; i++) {
jlen = pntsArr[i].length();
/*
if (jlen == 1) {
paramsArr[i].setLogicalLength(1);
continue;
}
*/
for (j=0; j<jlen; j++) {
pnt3d = surf.closestPointTo(pntsArr[i].at(j));
surf.isOn(pnt3d,param);
// param = surf.paramOf(pnt3d);
paramsArr[i].append(param);
}
}
// 判断曲面的奇异性,是否有边退化为点
AcGeInterval intrvlX,intrvlY;
surf.getEnvelope(intrvlX,intrvlY);
int nSigularity=0;
AcGePoint3d p1,p2,p3,p4,oSigularity;
// AcGePoint2d param;
p1 = surf.evalPoint(param.set(intrvlX.lowerBound(),intrvlY.lowerBound()));
p2 = surf.evalPoint(param.set(intrvlX.upperBound(),intrvlY.lowerBound()));
p3 = surf.evalPoint(param.set(intrvlX.upperBound(),intrvlY.upperBound()));
p4 = surf.evalPoint(param.set(intrvlX.lowerBound(),intrvlY.upperBound()));
if (p1.isEqualTo(p2)) {
nSigularity = 1;
oSigularity = p1;
} else if (p2.isEqualTo(p3)) {
nSigularity = 2;
oSigularity = p2;
} else if (p3.isEqualTo(p4)) {
nSigularity = 3;
oSigularity = p3;
} else if (p4.isEqualTo(p1)) {
nSigularity = 4;
oSigularity = p4;
}
if (nSigularity) {
AcGeLine2d l2;
AcGeLineSeg2d l1;
AcGePoint2d tp1,tp2;
switch(nSigularity) {
case 1:
tp1.set(intrvlX.lowerBound(),intrvlY.lowerBound());
tp2.set(intrvlX.upperBound(),intrvlY.lowerBound());
l1.set(tp1,tp2);
break;
case 2:
tp1.set(intrvlX.upperBound(),intrvlY.lowerBound());
tp2.set(intrvlX.upperBound(),intrvlY.upperBound());
l1.set(tp1,tp2);
break;
case 3:
tp1.set(intrvlX.upperBound(),intrvlY.upperBound());
tp2.set(intrvlX.lowerBound(),intrvlY.upperBound());
l1.set(tp1,tp2);
break;
case 4:
tp1.set(intrvlX.lowerBound(),intrvlY.upperBound());
tp2.set(intrvlX.lowerBound(),intrvlY.lowerBound());
l1.set(tp1,tp2);
break;
}
AcGePoint3dArray tmpPnts;
AcGePoint2dArray params;
for (i=0; i<len; i++) {
// 针对数组的首位进行判断
tmpPnts = pntsArr[i];
params = paramsArr[i];
if (tmpPnts[0].isEqualTo(oSigularity)) {
l2.set(params[1],params[2]);
if (!l1.intersectWith(l2,params[0])) {
double s1;
s1 = (tmpPnts[0]-tmpPnts[1]).length() / (tmpPnts[1]-tmpPnts[2]).length();
params[0] = params[1] + (params[1]-params[2])*s1;
params[0] = l1.closestPointTo(params[0]);
}
}
// 针对数组的第二位进行判断
if (tmpPnts[1].isEqualTo(oSigularity)) {
l2.set(params[0],params[1]);
if (!l1.intersectWith(l2,params[1])) {
double s1;
s1 = (tmpPnts[1]-tmpPnts[0]).length() / (tmpPnts[2]-tmpPnts[0]).length();
params[1] = params[0] + (params[2]-params[0])*s1;
params[1] = l1.closestPointTo(params[1]);
}
}
jlen = tmpPnts.length();
// 针对其他
for (j=2; j<jlen; j++) {
if (tmpPnts[j].isEqualTo(oSigularity)) {
l2.set(params[j-1],params[j-2]);
if (!l1.intersectWith(l2,params[j])) {
double s1;
s1 = (tmpPnts[j-1]-tmpPnts[j-2]).length() / (tmpPnts[j-1]-tmpPnts[j-2]).length();
params[j] = params[j-1] + (params[j-1]-params[i-2])*s1;
params[j] = l1.closestPointTo(params[j]);
}
}
}
paramsArr[i] = params;
}
}
if (bLoop) {
len = paramsArr.length();
if (len<1) return false;
AcGePoint2dArray params;
params.setLogicalLength(2);
if (!paramsArr.first().first().isEqualTo(paramsArr.last().last())) {
if (pntsArr.first().first().isEqualTo(oSigularity)) {
params[0] = paramsArr.last().last();
params[1] = paramsArr.first().first();
paramsArr.append(params);
} else {
paramsArr.last().append(paramsArr.first().first());
}
}
for (i=0; i<len-1; i++) {
if (!paramsArr[i].last().isEqualTo(paramsArr[i+1].first())) {
if (pntsArr[i].last().isEqualTo(oSigularity)) {
params[0] = paramsArr[i].last();
params[1] = paramsArr[i+1].first();
paramsArr.insertAt(i+1,params);
i++;
len++;
} else {
paramsArr[i].append(paramsArr[i+1].first());
}
}
}
}
return true;
}
bool getPntsArrayFromParamsArray(const AcGeNurbSurface& surf,const ChGePnts2dArray& paramsArr,ChGePnts3dArray& pntsArr)
{
if (!paramsArr.length()) return false;
int i,len,j,jlen;
len = paramsArr.length();
pntsArr.setLogicalLength(len);
for (i=0; i<len; i++) {
jlen = paramsArr[i].length();
pntsArr[i].setLogicalLength(jlen);
for (j=0; j<jlen; j++) {
(pntsArr[i])[j] = surf.evalPoint(paramsArr[i].at(j));
}
}
return true;
}
bool getLoopFromIntervalXY(const AcGeInterval& intrvX, const AcGeInterval& intrvY,ChGeLoop2d& loop, int nX, int nY)
{
if (!intrvX.isBounded() || !intrvY.isBounded()) return false;
if (nX<1 || nY<1) return false;
AcGePoint2dArray pnts2d;
AcGePoint2d tmpPnt;
double minX,maxX,minY,maxY,stepX,stepY;
int i;
minX = intrvX.lowerBound();
maxX = intrvX.upperBound();
minY = intrvY.lowerBound();
maxY = intrvY.upperBound();
stepX = intrvX.length()/nX;
stepY = intrvY.length()/nY;
loop.setLogicalLength(0);
pnts2d.setLogicalLength(nX+1);
tmpPnt.y = minY;
for (i=0; i<nX+1; i++) {
tmpPnt.x = minX+i*stepX;
pnts2d[i] = tmpPnt;
}
loop.append(pnts2d);
pnts2d.setLogicalLength(nY+1);
tmpPnt.x = maxX;
for (i=0; i<nY+1; i++) {
tmpPnt.y = minY+i*stepY;
pnts2d[i] = tmpPnt;
}
loop.append(pnts2d);
pnts2d.setLogicalLength(nX+1);
tmpPnt.y = maxY;
for (i=0; i<nX+1; i++) {
tmpPnt.x = maxX-i*stepX;
pnts2d[i] = tmpPnt;
}
loop.append(pnts2d);
pnts2d.setLogicalLength(nY+1);
tmpPnt.x = minX;
for (i=0; i<nY+1; i++) {
tmpPnt.y = maxY-i*stepY;
pnts2d[i] = tmpPnt;
}
loop.append(pnts2d);
/*
pnts2d[0].set(intrvX.lowerBound(),intrvY.upperBound());
pnts2d[1].set(intrvX.lowerBound(),intrvY.lowerBound());
loop[0] = pnts2d;
pnts2d[0].set(intrvX.lowerBound(),intrvY.lowerBound());
pnts2d[1].set(intrvX.upperBound(),intrvY.lowerBound());
loop[1] = pnts2d;
pnts2d[0].set(intrvX.upperBound(),intrvY.lowerBound());
pnts2d[1].set(intrvX.upperBound(),intrvY.upperBound());
loop[2] = pnts2d;
pnts2d[0].set(intrvX.upperBound(),intrvY.upperBound());
pnts2d[1].set(intrvX.lowerBound(),intrvY.upperBound());
loop[3] = pnts2d;
*/
return true;
}
bool isHead(const AcGePoint3dArray& curve, const AcGePoint3d& dirPnt)
{
AcGeNurbCurve3d crv(curve);
AcGePoint3d pnt;
pnt = crv.closestPointTo(dirPnt);
double p1;
crv.isOn(pnt,p1);
if (p1 < crv.endParam()/2 ) {
return true;
} else {
return false;
}
}
bool evalShapeCenterAndArea(const ChGeLoop2d& loop, AcGePoint2d& center, double& area)
{
if (loop.length()==0) return false;
double dA,Sx=0,Sy=0,A=0;
AcGePoint2d p1,p2;
int i,len,jlen;
len = loop.length();
for (i=0; i<len; i++) {
jlen = loop[i].length();
for (register j=1; j<jlen; j++) {
p2 = loop[i].at(j);
p1 = loop[i].at(j-1);
dA = (p2.x - p1.x) * (p2.y + p1.y) / 2;
A += dA;
Sy += dA * (p2.x + p1.x) / 2;
Sx += dA * (p2.y + p1.y) / 4;
}
}
if (fabs(A) < TOL5) return false;
center.set(Sy/A,Sx/A);
area = fabs(A);
return true;
}
bool evalShapeCenterAndArea(const AcGePoint2dArray& vertexs, AcGePoint2d& center, double& area)
{
if (vertexs.length()==0) return false;
double dA,Sx=0,Sy=0,A=0;
int i,len;
len = vertexs.length();
for (i=1; i<len; i++) {
dA = (vertexs[i].x - vertexs[i-1].x)
* (vertexs[i].y + vertexs[i-1].y) / 2;
A += dA;
Sy += dA * (vertexs[i].x + vertexs[i-1].x) / 2;
Sx += dA * (vertexs[i].y + vertexs[i-1].y) / 4;
}
dA = (vertexs.first().x - vertexs.last().x)
* (vertexs.first().y + vertexs.last().y) / 2;
A += dA;
Sy += dA * (vertexs.first().x + vertexs.last().x) / 2;
Sx += dA * (vertexs.first().y + vertexs.last().y) / 4;
if (fabs(A) < TOL5) return false;
center.set(Sy/A,Sx/A);
area = fabs(A);
return true;
}
// 图形是否以某条线为轴对称
bool isAxialSymmetric(const AcGePoint2dArray& vertexs, const AcGeLine2d& line)
{
if (vertexs.length()<2) return false;
AcGePoint2d symPnt;
int i,len;
AcGePoint2dArray vertexsCopy;
len = vertexs.length();
for (i=0; i<len; i++) {
vertexsCopy = vertexs;
symPnt = vertexs[i];
symPnt.mirror(line);
vertexsCopy.removeAt(i);
if (!vertexs.contains(symPnt)) {
return false;
}
}
return true;
}
Acad::ErrorStatus
getBaseSurface(AcDbEntity* pSurf,
AcGeNurbSurface& baseSurf,
Adesk::Boolean* pbIsSame)
{
// 得到曲面的BrFace
AcBr::ErrorStatus brEs;
AcBrFace *pFace;
brEs = getBrEntityFromEnt(pSurf,
AcDb::kFaceSubentType,(AcBrEntity*&)pFace);
if (brEs != AcBr::eOk)
return Acad::eInvalidInput;
// 得到曲面的ExternalBoundedSurface
Adesk::UInt32 num;
AcGeExternalBoundedSurface exsurf,**ppNurbs=NULL;
if (pbIsSame) {
Adesk::Boolean bIsSame;
pFace->getOrientToSurface(bIsSame);
*pbIsSame = bIsSame;
}
pFace->getSurfaceAsTrimmedNurbs(num,ppNurbs);
if (num>1) {
delete [] ppNurbs;
return Acad::eWrongObjectType;
} else if (num==0) {
return Acad::eWrongObjectType;
}
delete pFace;
exsurf = *ppNurbs[0];
delete [] ppNurbs;
// 得到曲面的BaseSurface
AcGeNurbSurface *pBaseSurf=NULL;
exsurf.getBaseSurface((AcGeSurface*&)pBaseSurf);
baseSurf = *pBaseSurf;
delete pBaseSurf;
return Acad::eOk;
}
Acad::ErrorStatus
getBaseSurfaceAndLoops(AcDbEntity* pSurf,
AcGeNurbSurface& baseSurf,
ChGeLoop3dArray& loops,
Adesk::Boolean* pbIsSame)
{
// 得到曲面的BrFace
AcBr::ErrorStatus brEs;
AcBrFace *pFace;
brEs = getBrEntityFromEnt(pSurf,
AcDb::kFaceSubentType,(AcBrEntity*&)pFace);
if (brEs != AcBr::eOk)
return Acad::eInvalidInput;
// 得到原曲面的loops
AcBrLoopPointerArray Loops;
getBrLoopsFromBrFace(pFace,Loops);
loops.setLogicalLength(0);
getGeLoopsFromBrLoops(Loops,loops);
int i,len;
len = Loops.length();
for (i=0; i<len; i++) {
delete (AcBrLoop*)(Loops[i]);
}
// 得到曲面的ExternalBoundedSurface
Adesk::UInt32 num;
AcGeExternalBoundedSurface exsurf,**ppNurbs=NULL;
if (pbIsSame) {
Adesk::Boolean bIsSame;
pFace->getOrientToSurface(bIsSame);
*pbIsSame = bIsSame;
}
pFace->getSurfaceAsTrimmedNurbs(num,ppNurbs);
if (num>1) {
delete [] ppNurbs;
return Acad::eWrongObjectType;
} else if (num==0) {
return Acad::eWrongObjectType;
}
delete pFace;
exsurf = *ppNurbs[0];
delete [] ppNurbs;
// 得到曲面的BaseSurface
AcGeNurbSurface *pBaseSurf=NULL;
exsurf.getBaseSurface((AcGeSurface*&)pBaseSurf);
baseSurf = *pBaseSurf;
delete pBaseSurf;
return Acad::eOk;
}
/*
bool getLoopFromVertexs(const AcGePoint2dArray& vertexs, const AcGePoint2d& ptInLoop, ChGeLoop2d& loop)
{
int i,len;
len = vertexs.length();
if (len<3) return false;
AcGePoint2d pt;
pt.set(ptInLoop.x,-1.7e308);
AcGeRay2d ptRay(ptInLoop,pt);
AcGePoint2d intPt,maxYPt,tmpPt; // 交点, Y值最大的交点
int maxYPtIndex; // 交点所在直线的索引号
AcGeLineSeg2d *pLineSeg;
AcGeVoidPointerArray pLines; // 所有的直线段
pLines.setLogicalLength(len-1);
for (i=1; i<len; i++) {
pLineSeg = new AcGeLineSeg2d(vertexs[i-1],vertexs[i]);
pLines[i-1] = pLineSeg;
}
// 得到与射线的交点Y值最大的直线索引号和交点
maxYPtIndex = -1;
len = pLines.length();
for (i=0; i<len; i++) {
pLineSeg = (AcGeLineSeg2d*) pLines[i];
if (ptRay.intersectWith(*pLineSeg,intPt)) {
if (maxYPtIndex == -1) {
maxYPtIndex = i;
maxYPt = intPt;
} else {
if (maxYPt.y < intPt.y) {
maxYPtIndex = i;
maxYPt = intPt;
}
}
}
}
if (maxYPtIndex == -1) {
// 不存在这样的点则表示不存在包含ptInLoop的Loop存在
return false;
}
// 将交点所在直线段分为两段(可能的话)
pLineSeg = (AcGeLineSeg2d*) pLines[maxYPtIndex];
if (pLineSeg->endPoint().isEqualTo(maxYPt)) {
maxYPtIndex++;
if (maxYPtIndex==len) {
maxYPtIndex = 0;
}
} else if (!pLineSeg->startPoint().isEqualTo(maxYPt)) {
tmpPt = pLineSeg->startPoint();
pLineSeg->set(maxYPt,pLineSeg->endPoint());
pLineSeg = new AcGeLineSeg2d(tmpPt,maxYPt);
pLines.insertAt(maxYPtIndex,pLineSeg);
maxYPtIndex++;
}
AcGePoint2dArray validVertexs; // 所有有效顶点
validVertexs.append(maxYPt);
// 整理直线数组,以index所在的直线段为头
AcGeVoidPointerArray realLines;
len = pLines.length();
for (i=maxYPtIndex; i<len; i++) {
realLines.append(pLines[i]);
}
for (i=0; i<maxYPtIndex; i++) {
realLines.append(pLines[i]);
}
AcGePoint2dArray intPts; // 所有与当前直线的交点
AcGeIntArray intIndexs; // 所有交点所在的直线索引号
AcGeLineSeg2d *pTmpLine, *pOverLap;
Adesk::Boolean bRet;
int j;
len = pLines.length();
pLineSeg = (AcGeLineSeg2d*) realLines[0];
for (i=2; i<len; i++) {
pTmpLine = (AcGeLineSeg2d*) realLines[i];
if (pLineSeg->overlap(pTmpLine,(AcGeLinearEnt2d*&)pOverLap)) {
// 判断重合
if (pOverLap->direction().isCodirectionalTo(pTmpLine->direction())) {
intPts.append(pOverLap->endPoint());
intIndexs.append(i);
} else {
intPts.append(pOverLap->startPoint());
}
intIndexs.append(i);
delete pOverLap;
} else {
// 判断相交
bRet = pLineSeg->intersectWith(pTmpLine,intPt);
if (!bRet) continue;
if (intPt.isEqualTo(pTmpLine->endPoint())) {
if (i==len-1) {
intIndexs.append(0);
} else {
intIndexs.append(i+1);
}
} else {
intIndexs.append(i);
}
intPts.append(intPt);
}
}
len = intPts.length();
if (len==0) continue;
double param,minParam;
int minIndex;
minParam = pLineSeg->paramOf(intPts[0]);
minIndex = 0;
for (i=1; i<len; i++) {
param = pLineSeg->paramOf(intPts[i]);
if (param<minParam) {
minParam = param;
minIndex = i;
}
}
intIndexs.removeAt(minIndex);
intPt = intPts[minIndex];
return true;
}*/
|
|