Bryco 发表于 2007-6-23 11:34:36

AcDb MPolygon-MPolygon内部的点可靠吗?

我一直在考虑使用AcDbMPolygon类和isPointInsideMPolygon()来验证一个点是否在一条轻量级折线内,但是由于某种原因对我不起作用。
例如,我选择了一组多段线,如果我定义了一个内部点,我希望获得该多段线,即该内部点所在的位置。
下面是一个命令示例:
      static void LESQGBPoly17_GETPOLY(void)
      {
                ads_name sspol;
                resbuf *rbFilter = acutBuildList(RTDXF0, _T("LWPOLYLINE"), RTNONE);
                if (acedSSGet(NULL, NULL, NULL, rbFilter, sspol) != RTNORM)
                {
                        acutRelRb(rbFilter); return;
                }
                acutRelRb(rbFilter);
                long len = 0;
                if ((acedSSLength(sspol, &len) != RTNORM) || (len == 0))
                {
                        acedSSFree(sspol); return;
                }
                AcGePoint3d worldPt;
                if (acedGetPoint(NULL,_T("\nPick internal point: "),asDblArray(worldPt)) != RTNORM) return;
                for (int i=0; i pPoly(objId, AcDb::kForWrite);//for write test to erase, or color change
                        if (pPoly.openStatus() == Acad::eOk)
                        {
                              acdbUcs2Wcs(asDblArray(worldPt),asDblArray(worldPt),false);
                              AcGeVector3d vDir = AcGeVector3d::kZAxis;
                              resbuf rb; acedGetVar(_T("viewdir"),&rb);
                              vDir = asVec3d(rb.resval.rpoint);
                              AcDb::Planarity plan_type;
                              AcGePlane plane;
                              pPoly->getPlane(plane,plan_type);
                              worldPt = worldPt.project(plane,vDir);
                              AcGeIntArray loopsArray; //loopsArray.setLogicalLength(0);
                              if (mpol.appendLoopFromBoundary(pPoly) == Acad::eOk)
                              {
                                        if ( mpol.isPointInsideMPolygon(worldPt, loopsArray) > 0)
                                        {
                                                acutPrintf(_T("\nPoint inside..."));
                                                pPoly.object()->setColorIndex(6);
                                        }
                              }
                        }
                }
                acedSSFree(sspol);
      }


但是,如果当我尝试在附着的图形中的洋红色多段线中定义内部点时,它不会返回true,除非我在isPointInsideMPolygon(worldPt,loopsArray,1.0)中更改容差以添加1.0,例如,它会返回该点在内部,但也会获得选择中的其他多段线(这是我不希望的)。所以现在,我很困惑...
有人有使用isPointInsideMPolygon()的经验吗?我知道Alexander Rivilis在这里发布的函数是_point_in_curve(),但它也有相同的结果...
谢谢!
**** Hidden Message *****

MickD 发表于 2007-6-24 23:33:12

乐,我有一个vba版本,但我还在努力把它转换成C#。
http://soft surfer . com orientation 2d _ Polygon()具有用于直线的数学运算
并且我添加了用于曲线的数学运算。

Bryco 发表于 2007-6-25 00:25:46

这可能与多边形的“缠绕”有关吗,即。它的顶点与围绕它的其他多边形的方向相反?如果是这种情况,那么它周围的所有多边形都将返回true。
只是一个猜测,但由于红色多边形在所有其他多边形中,这是您之前的多边形函数的结果,您可能需要反转顶点?

T.Willey 发表于 2007-6-25 09:10:07


布莱科
我将研究该链接……我为我的gbpoly项目完成了一些功能,这些功能对这一点很有用,我希望它使用ARX类中可用的功能。

T.Willey 发表于 2007-6-25 09:11:40


你好,米克;
根据adesk的arx新闻组中Alexander Rivilis的回答,似乎或者更确切地说,这是类中的一个错误。
谢谢!

MickD 发表于 2007-6-25 09:56:14

半年前,我将此错误发布到ADN。有趣的是,在AutoCAD 2006中,此代码可以毫无问题地工作。新版本-新错误...
P. S.:尝试此代码:
static void BrepPointCheckPoint(void)
{
Acad::ErrorStatus es;
AcBr::ErrorStatus ebr;
ads_name en;
ads_point pt;
if (acedEntSel(_T("\nSelect contour: "), en, pt) != RTNORM)
    return;
AcDbObjectId eId; acdbGetObjectId(eId,en);
AcDbObjectPointer pline(eId,AcDb::kForRead) ;
if ((es = pline.openStatus()) != Acad::eOk) {
    acutPrintf(_T("\npline.openStatus()=%s"),acadErrorStatusText(es));
    return;
}
if (acedGetPoint(pt,_T("\nPick point: "), pt) != RTNORM)
    return;
AcDbVoidPtrArray ar, regions;
ar.append(pline.object());
if ((es = AcDbRegion::createFromCurves(ar,regions)) != Acad::eOk){
    acutPrintf(_T("\nAcDbRegion::createFromCurves(ar,regions)=%s"),acadErrorStatusText(es));
    return;
}
AcDbRegion reg; reg.copyFrom((AcDbRegion *)regions);
for (int i=0; i<regions.length();i++) delete regions;
AcBrBrep brEnt;ebr = brEnt.set(reg);
if (ebr != AcBr::eOk) {
    acutPrintf(_T("\nbrEnt.set(sol)=%s"),acadErrorStatusText((Acad::ErrorStatus)(Adesk::UInt32)ebr));
    return;
}
AcGe::PointContainment pDesc;
AcBrEntity *pCont = NULL;
AcBrBrepFaceTraverser brepFaceTrav; brepFaceTrav.setBrep(brEnt);
AcBr::ErrorStatus err = AcBr::eInvalidInput;
while (!brepFaceTrav.done()) {
   AcBrFace brFace; brepFaceTrav.getFace(brFace);
   err = brFace.getPointContainment(asPnt3d(pt),pDesc,pCont);
   if (err == Acad::eOk && pDesc == AcGe::kInside) {
   acedAlert(_T("In")); return;
   } else if (err == Acad::eOk && pDesc == AcGe::kOnBoundary) {
   acedAlert(_T("On")); return;
   }
   brepFaceTrav.next();
}
if (err == Acad::eOk) {
    acedAlert(_T("Out"));
} else {
    acedAlert(_T("Unknown error"));
}
return;
}

MickD 发表于 2007-6-25 10:27:22

谢谢你,亚历山大
我稍后在家里尝试一下……我发现需要使用区域……
是的,它们会打开一个新孔来覆盖上一个孔……(用于虫子)

T.Willey 发表于 2007-6-26 17:45:45

这是我最终使用的,它基于John F. Uhden
的算法编辑:函数isPointIn()现在可以用于封闭曲线类对象-Polyline(样条和拟合),LWPolyline(样条和拟合),圆圈和样条,添加了更多控件。-上传为CPP文件
LE!

Bryco 发表于 2007-6-28 01:00:23

在完成上一个函数之后,现在我已经能够提出自己的边界/ bpoly命令,名为GETPOLY,如果可以的话,看看正在进行的结果......现在我需要知道如何为C#传递这个新函数...

T.Willey 发表于 2007-6-28 01:14:53

对猫来说很酷路易斯
页: [1] 2
查看完整版本: AcDb MPolygon-MPolygon内部的点可靠吗?