highflyingbird 发表于 2010-6-10 03:37:29

如何从AcDb2dPolyline对象中获取AcGeCurve3d对象?

如何获取与AcDb2dPolyline对象关联的AcGeCurve3d对象?
例如,是否有一个名为“AcDb2dPolylineToAcGeCurve3d(AcDb2dPolyline*, AcGeCurve3d * & )"?
顺便说一下,我可以从其他类型的曲线(折线、圆、样条...)中获取AcGeCurve3d,但为此,我找不到方法。
**** Hidden Message *****

pkohut 发表于 2010-6-10 05:40:21

如果可以从多段线获取AcGeCurve3d,并且AcDb2dPolyline很简单,则可以在AcDbPolyline::convertFrom的帮助下将其转换为AcDbPolyline。如果AcDb2dPolyline不简单,可以尝试使用AcDbCurve::getSpline方法将其转换为样条线。

highflyingbird 发表于 2010-6-10 05:48:42

没有了。
不知道。
怎么知道?你能提供一个代码样本吗?您总是可以使用AcDbPolyline::convertFrom函数将AcDb2dPolyline转换为AcDbPolyline,并从那里通过任何方式获得AcGeCurve3d对象。

pkohut 发表于 2010-6-10 06:14:51

好的,这是我的代码。
#definePI 3.14159265358979323846264338327950288
//转换AcDbCurve到AcGeCurve3d
//Function : Get AcGeCurve3d object associated with AcDbCurve (include : line,arc,circle,ellipse,spline,polyline...)
//Arguments: from : AcDbCurve , the AcDbCurbe object,to : AcGeCurve3d object
//return:Acad::ErrorStatus
Acad::ErrorStatus convertDbCurveToGeCurve(AcDbCurve *pDbCurve,AcGeCurve3d *&pGeCurve)
{
        pGeCurve=NULL;
        // for Line: is very simple;
        if (pDbCurve->isKindOf(AcDbLine::desc()))
        {
                AcDbLine *pL=(AcDbLine *)pDbCurve;
                AcGeLineSeg3d *pGL=new AcGeLineSeg3d;
                pGL->set(pL->startPoint(),pL->endPoint());
                pGeCurve=(AcGeCurve3d *)pGL;
        }
        // for Arc;
        else if (pDbCurve->isKindOf(AcDbArc::desc()))
        {
                AcDbArc *pArc=(AcDbArc *)pDbCurve;
                double ans,ane;
                ans=pArc->startAngle();
                ane=pArc->endAngle();
                AcGeCircArc3d *pGArc=new AcGeCircArc3d;
                pGArc->setCenter(pArc->center());
                pGArc->setRadius(pArc->radius());
                pGArc->setAngles(ans,ane);
                pGeCurve=(AcGeCurve3d *)pGArc;
        }
        // for Circle;
        else if (pDbCurve->isKindOf(AcDbCircle::desc()))
        {
                AcDbCircle *pCir=(AcDbCircle *)pDbCurve;
                AcGeCircArc3d * pGCir=new AcGeCircArc3d;
                pGCir->setCenter(pCir->center());
                pGCir->setRadius(pCir->radius());
                pGeCurve=(AcGeCurve3d *)pGCir;
        }
        //for Ellipse
        else if (pDbCurve->isKindOf(AcDbEllipse::desc()))
        {
                AcDbEllipse *pEli=(AcDbEllipse *)pDbCurve;
                AcGePoint3d center=pEli->center();
                AcGeVector3d pv1 = pEli->majorAxis();
                double majorRadius = sqrt(pv1.x*pv1.x+pv1.y*pv1.y+pv1.z*pv1.z);
                double param1,param2;
                pEli->getStartParam(param1);
                pEli->getEndParam(param2);
                AcGeEllipArc3d *pGEli=new AcGeEllipArc3d;
                pGEli->setCenter(center);
                pGEli->setAxes(pv1,pEli->minorAxis());       
                pGEli->setMajorRadius(majorRadius);
                pGEli->setMinorRadius(majorRadius*(pEli->radiusRatio()));
                pGEli->setAngles(param1,param2);
                pGeCurve=(AcGeCurve3d *)pGEli;
        }
        //for Spline
        else if (pDbCurve->isKindOf(AcDbSpline::desc()))
        {
                AcDbSpline *pSL=(AcDbSpline *)pDbCurve;
                if (!pSL)
                {       
                        return Acad::eNotImplemented;
                }
                if (pSL->isNull()==Adesk::kTrue)
                {
                        return Acad::eNotImplemented;
                }
                int degree;
                Adesk::Boolean rational;
                Adesk::Boolean closed;
                Adesk::Boolean periodic;
                AcGePoint3dArray controlPoints;
                AcGeDoubleArray knots;
                AcGeDoubleArray weights;
                double controlPtTol;
                double knotTol;
                AcGeTol tol;
                Acad::ErrorStatus es;
                es=pSL->getNurbsData(degree,rational,closed,periodic,controlPoints,knots,weights,controlPtTol,knotTol);
                if (es!=Acad::eOk)
                {
                        return Acad::eNotImplemented;
                }
                       
                if (rational==Adesk::kTrue)
                {
                        AcGeNurbCurve3d *pNurb=new AcGeNurbCurve3d(degree,knots,controlPoints,weights,periodic);
                        pGeCurve=(AcGeCurve3d *)pNurb;
                }
                else
                {
                        AcGeNurbCurve3d *pNurb=new AcGeNurbCurve3d(degree,knots,controlPoints,periodic);
                        pGeCurve=(AcGeCurve3d *)pNurb;
                }
        }
        // for Polyline
        else if (pDbCurve->isKindOf(AcDbPolyline::desc()))
        {
                AcDbPolyline *pPoly = (AcDbPolyline *)pDbCurve;
                int nSegs;
                AcGeLineSeg3d *pLine;
                AcGeLineSeg3d line;
                AcGeCircArc3d *pArc;
                AcGeCircArc3d arc;
                AcGeVoidPointerArray geCurves;
                if (pPoly->isClosed())
                {
                        nSegs = pPoly->numVerts();
                }
                else
                {
                        nSegs = pPoly->numVerts() - 1;
                }
               
                for( int i = 0; i segType(i) == AcDbPolyline::kLine )
                        {
                                pPoly->getLineSegAt( i, line );
                                pLine = new AcGeLineSeg3d( line );
                                geCurves.append( pLine );
                        }
                        else if( pPoly->segType( i ) == AcDbPolyline::kArc )
                        {
                                pPoly->getArcSegAt( i, arc );
                                pArc = new AcGeCircArc3d( arc );
                                geCurves.append( pArc );
                        }
                }
                if( geCurves.length() == 1 )
                {
                        pGeCurve = ( AcGeCurve3d* )( geCurves );
                }
                else
                {
                        pGeCurve = new AcGeCompositeCurve3d( geCurves );
                }
        }
        //else if (pDbCurve->isKindOf(AcDb2dPolyline::desc()))
        //{
        //}
        return (pGeCurve)?Acad::eOk:Acad::eNotImplemented;
}
我没有完成关于AcDb2dPolyline的部分代码,我希望AcGeCurve3d对象完全来自AcDbCurve对象,而不是合适的对象。

highflyingbird 发表于 2010-6-10 06:25:40

是的,好的。继续处理转换过程。将AcDbPolyline::convertFrom与AcDb2dPolyline一起使用,并称之为良好。

highflyingbird 发表于 2010-6-10 06:47:48

AcDbSpline的代码不是通用的(恕我直言)。查看: http://www.caduser.ru/forum/index.php?PAGE_NAME=message&FID=24&TID=22185&MID=125061#message125061

pkohut 发表于 2010-6-10 07:04:18

我有一个方法,如果AcDb2dPolyline不简单:
                AcDbObjectIterator *pVertIter = NULL;
               
                pVertIter=p2dPoly->vertexIterator();
                AcDb2dVertex *pVertex = NULL;
                AcDbObjectId vertId;
                AcGePoint3d pt;
                AcGePoint3dArray ptArray;
                for(pVertIter->start();!pVertIter->done();pVertIter->step())
                {
                        vertId = pVertIter->objectId();
                        acdbOpenObject(pVertex,vertId,AcDb::kForRead);
                        pt=pVertex->position();
                        ptArray.append(pt);
                        pVertex->close();
                }
这样,我得到了点,所以我可以构造段,然后我可以构造AcGeCurve3d

highflyingbird 发表于 2010-6-10 07:09:32

它仅适用于不带凸出的<strong>简单<AcDb2dPolyline。阅读有关AcDb2dPolyline::polyType方法的信息。

highflyingbird 发表于 2010-6-10 07:15:49


我还是有点困惑,谢谢你,还有佩克胡特isKindOf(AcDbLine::desc())) ...
else if (pDbCurve->isKindOf(AcDbArc::desc())) ...
else if (pDbCurve->isKindOf(AcDbCircle::desc())) ...
else if (pGrass->isGreener(AcDbThatField::desc()))...

这种类型的代码不是必需的。 当你发现自己在做一堆 isKindOf 函数时,问问自己是否有更好的方法来编写代码。在你的情况下有。将它们中的每一个分解成自己的小函数,让C++函数重载来完成所有工作。代码将更易于维护且速度更快。
仅供参考,在AcDbPolyline的测试中,您为局部变量分配了一个返回的引用
AcGeVoidPointerArray geCurves; ... pGeCurve = ( AcGeCurve3d* )( geCurves );
当convertDbCurveToGeCurve超出范围时,geCurves也是如此。这些类型的错误可能很难追踪。
下面是使用函数重载对代码进行重构,它可能无法编译或工作,因为我刚刚重新组织了一下。
AcGeLineSeg3d * convertDbCurveToGeCurve3d(const AcDbLine * pLine)
{
    AcGeLineSeg3d * pGL = new AcGeLineSeg3d;
    pGL->set(pLine->startPoint(), pLine->endPoint());
    return pGL;
}
AcGeCircArc3d * convertDbCurveToGeCurve3d(const AcDbArc * pArc)
{
    //                AcDbArc *pArc=(AcDbArc *)pDbCurve;
    double ans,ane;
    ans=pArc->startAngle();
    ane=pArc->endAngle();
    AcGeCircArc3d *pGArc=new AcGeCircArc3d;
    pGArc->setCenter(pArc->center());
    pGArc->setRadius(pArc->radius());
    pGArc->setAngles(ans,ane);
    return pGArc;
}
AcGeCurve3d * Acad::ErrorStatus convertDbCurveToGeCurve3d(const AcDbCircle * pCircle)
{
    AcGeCircArc3d * pGCir=new AcGeCircArc3d;
    pGCir->setCenter(pCir->center());
    pGCir->setRadius(pCir->radius());
    return pGCir;
}
AcGeEllipArc3d * Acad::ErrorStatus convertDbCurveToGeCurve3d(const AcDbEllipArc3d * pEli)
{
    AcGePoint3d center=pEli->center();
    AcGeVector3d pv1 = pEli->majorAxis();
    double majorRadius = sqrt(pv1.x*pv1.x+pv1.y*pv1.y+pv1.z*pv1.z);
    double param1,param2;
    pEli->getStartParam(param1);
    pEli->getEndParam(param2);
    AcGeEllipArc3d *pGEli=new AcGeEllipArc3d;
    pGEli->setCenter(center);
    pGEli->setAxes(pv1,pEli->minorAxis());       
    pGEli->setMajorRadius(majorRadius);
    pGEli->setMinorRadius(majorRadius*(pEli->radiusRatio()));
    pGEli->setAngles(param1,param2);
    return pGEli;
}
AcGeNurbCurve3d * Acad::ErrorStatus convertDbCurveToGeCurve3d(const AcDbSpline * pSL)
{
    int degree;
    Adesk::Boolean rational;
    Adesk::Boolean closed;
    Adesk::Boolean periodic;
    AcGePoint3dArray controlPoints;
    AcGeDoubleArray knots;
    AcGeDoubleArray weights;
    double controlPtTol;
    double knotTol;
    AcGeTol tol;
    Acad::ErrorStatus es;
    es=pSL->getNurbsData(degree,rational,closed,periodic,controlPoints,knots,weights,controlPtTol,knotTol);
    if (es!=Acad::eOk)
    {
      return NULL;
    }
    AcGeNurbeCurve3d * pNurb = NULL;                       
    if (rational==Adesk::kTrue)
    {
      pNurb=new AcGeNurbCurve3d(degree,knots,controlPoints,weights,periodic);
    }
    else
    {
      pNurb=new AcGeNurbCurve3d(degree,knots,controlPoints,periodic);
    }
    return pNurb;
}
AcGeCompositeCurve3d * Acad::ErrorStatus convertDbCurveToGeCurve3d(const AcDbPolyline * pPoly)
{
    int nSegs;
    AcGeLineSeg3d *pLine;
    AcGeLineSeg3d line;
    AcGeCircArc3d *pArc;
    AcGeCircArc3d arc;
    AcGeVoidPointerArray * geCurves = new AcGeVoidPointerArray;
    if (pPoly->isClosed())
    {
      nSegs = pPoly->numVerts();
    }
    else
    {
      nSegs = pPoly->numVerts() - 1;
    }
    for( int i = 0; i segType(i) == AcDbPolyline::kLine )
      {
            pPoly->getLineSegAt( i, line );
            pLine = new AcGeLineSeg3d( line );
            geCurves->append( pLine );
      }
      else if( pPoly->segType( i ) == AcDbPolyline::kArc )
      {
            pPoly->getArcSegAt( i, arc );
            pArc = new AcGeCircArc3d( arc );
            geCurves->append( pArc );
      }
    }
    if(geCurves.IsEmpty()) {
      delete pGeCurves;
      return NULL;
    }
    return new AcGeCompositeCurve3d( geCurves );
}
AcGeEntity3d * convertDbCurveToGeCurve3d(const AcDbCurve *pDbCurve)
{
    // catch all for all other entity types.
    return NULL;
}

highflyingbird 发表于 2010-6-10 07:57:37


非常感谢,pkohut,太棒了!重载!万分感谢。
当2dPolyline是“k2dQuadSplinePoly”或“k2dCubicSplinePoly”时,我认为我的方法是正确的。我正在验证它。
页: [1] 2
查看完整版本: 如何从AcDb2dPolyline对象中获取AcGeCurve3d对象?