找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
热搜: 活动 交友 discuz
查看: 190|回复: 1

[每日一码] 转换ARC到POLYLINE

[复制链接]

0

主题

0

回帖

26

积分

管理员

积分
26
发表于 2024-2-23 22:37:51 | 显示全部楼层 |阅读模式
下面是使用命令pedit实现的连接LINE/ARC到POLYLINE的代码:
  1. //-----------------------------------------------------------------------------
  2. //----- acrxEntryPoint.cpp
  3. //-----------------------------------------------------------------------------
  4. #include "StdAfx.h"
  5. #include "acedCmdNF.h"
  6. #include "resource.h"
  7. //-----------------------------------------------------------------------------
  8. #define szRDS 采用RXST("")
  9. //-----------------------------------------------------------------------------
  10. //----- ObjectARX EntryPoint
  11. class CMyJoinApp : public AcRxArxApp {
  12. public:
  13.   CMyJoinApp() : AcRxArxApp() {}
  14.   virtual AcRx::AppRetCode On采用kInitAppMsg(void *pkt) {
  15.     AcRx::AppRetCode retCode = AcRxArxApp::On采用kInitAppMsg(pkt);
  16.     return (retCode);
  17.   }
  18.   virtual AcRx::AppRetCode On采用kUnloadAppMsg(void *pkt) {
  19.     AcRx::AppRetCode retCode = AcRxArxApp::On采用kUnloadAppMsg(pkt);
  20.     return (retCode);
  21.   }
  22.   virtual void RegisterServerComponents() {}
  23.   static void RivilisMyJoin() {
  24.     ads采用name en1;  ads采用point p;
  25.     while (acedEntSel(采用T("\nSelect first segment: "), en1, p) == RTNORM)
  26.     {
  27.       bool bConvertToPoly = false;
  28.       AcDbObjectId id1; acdbGetObjectId(id1, en1);
  29.       if (id1.objectClass() == AcDbLine::desc() ||
  30.           id1.objectClass() == AcDbArc::desc())
  31.       {
  32.         bConvertToPoly = true;
  33.       }
  34.       ads采用name en2;
  35.       if (acedEntSel(采用T("\nSelect next segment: "), en2, p) == RTNORM)
  36.       {
  37.         if (bConvertToPoly)
  38.           acedCommandS(RTSTR, 采用T("采用PEDIT"), RTENAME, en1, RTSTR, 采用T("采用YES"), RTSTR, 采用T("采用Join"),
  39.             RTENAME, en2, RTSTR, 采用T(""), RTSTR, 采用T(""), RTNONE);
  40.         else
  41.           acedCommandS(RTSTR, 采用T("采用PEDIT"), RTENAME, en1, RTSTR, 采用T("采用Join"),
  42.             RTENAME, en2, RTSTR, 采用T(""), RTSTR, 采用T(""), RTNONE);
  43.       }
  44.     }
  45.   }
  46. };
  47. //-----------------------------------------------------------------------------
  48. IMPLEMENT采用ARX采用ENTRYPOINT(CMyJoinApp)
  49. ACED采用ARXCOMMAND采用ENTRY采用AUTO(CMyJoinApp, Rivilis, MyJoin, MyJoin, ACRX采用CMD采用MODAL, NULL)
复制代码

0

主题

0

回帖

26

积分

管理员

积分
26
 楼主| 发表于 2024-2-23 22:38:47 | 显示全部楼层
下面是不用命令实现的连接LINE/ARC到POLYLINE的代码
  1. //-----------------------------------------------------------------------------
  2. //----- acrxEntryPoint.cpp
  3. //-----------------------------------------------------------------------------
  4. #include "StdAfx.h"
  5. #include "resource.h"
  6.   
  7. //-----------------------------------------------------------------------------
  8. #define szRDS 采用RXST("")
  9.   
  10. //-----------------------------------------------------------------------------
  11. //----- ObjectARX EntryPoint
  12. class CJoinToPlineApp : public AcRxArxApp {
  13.   
  14. public:
  15.   CJoinToPlineApp () : AcRxArxApp () {}
  16.   
  17.   virtual AcRx::AppRetCode On采用kInitAppMsg (void *pkt) {
  18.     AcRx::AppRetCode retCode = AcRxArxApp::On采用kInitAppMsg (pkt) ;
  19.     return (retCode) ;
  20.   }
  21.   
  22.   virtual AcRx::AppRetCode On采用kUnloadAppMsg (void *pkt) {
  23.     AcRx::AppRetCode retCode = AcRxArxApp::On采用kUnloadAppMsg (pkt) ;
  24.     return (retCode) ;
  25.   }
  26.   
  27.   virtual void RegisterServerComponents () {
  28.   }
  29.   
  30.   static void JoinToPlineJoinToPline () {
  31.     // Фильтр для выбора отрезков (LINE) и дуг (ARC)
  32.     ACHAR* promptPtrs[] = {
  33.       采用T("\nSelect lines and arcs for join in poyline (ENTER - exit): "),
  34.       采用T("\nRemove lines and arcs from selection set: ")
  35.     };
  36.   
  37.     ads采用name ss;
  38.     resbuf *rbFilter = acutBuildList(RTDXF0,采用T("LINE,ARC"),RTNONE);
  39.     int rc = acedSSGet(采用T(":$"),promptPtrs,NULL,rbFilter,ss);
  40.     acutRelRb(rbFilter);
  41.   
  42.     if (rc != RTNORM) return;
  43.   
  44.     AcDbObjectIdArray ids;
  45.     if (ObjectIdArrayFromSelSet(ss, ids) != Acad::eOk) return;
  46.     while (ids.length() > 0)
  47.     {
  48.       AcDbEntity *p = MakeJonedPoly(ids);
  49.       if (p) {
  50.         AcDbBlockTableRecordPointer pSpace(acdbCurDwg()->currentSpaceId(), AcDb::kForWrite);
  51.         if (pSpace.openStatus() != Acad::eOk) return;
  52.         pSpace->appendAcDbEntity(p);
  53.         p->close();
  54.       } else {
  55.         acutPrintf(采用T("\nError in data!"));
  56.         return;
  57.       }
  58.     }
  59.   
  60.   }
  61.   
  62.   /// <summary>
  63.   /// AcDbObjectIdArray from SelectionSet
  64.   /// </summary>
  65.   /// <param name="sset">SelectionSet</param>
  66.   /// <param name="ids">AcDbObjectIdArray</param>
  67.   /// <returns></returns>
  68.   static Acad::ErrorStatus ObjectIdArrayFromSelSet(ads采用name sset, AcDbObjectIdArray &ids)
  69.   {
  70.     Acad::ErrorStatus es = Acad::eOk;
  71.     long nset = -1;
  72.     if (acedSSLength(sset,&nset) != RTNORM) return Acad::eAmbiguousInput;
  73.     ids.setLogicalLength(nset);
  74.     ads采用name en;
  75.     AcDbObjectId id;
  76.     for (long i=0; i < nset; i++) {
  77.       if (acedSSName(sset,i,en) == RTNORM) {
  78.         if ((es = acdbGetObjectId(id,en)) != Acad::eOk) return es;
  79.         ids[i] = id;
  80.       }
  81.     }
  82.     return Acad::eOk;
  83.   }
  84.   
  85.   /// <summary>
  86.   /// Create polyline from lines and arcs.
  87.   /// Those ids will remove from input array
  88.   /// </summary>
  89.   /// <param name="ids">Array of id's</param>
  90.   /// <param name="FUZZ">The accuracy of determining the distance between points</param>
  91.   /// <returns></returns>
  92.   static AcDbPolyline* MakeJonedPoly(
  93.     AcDbObjectIdArray &ids,
  94.     double FUZZ = AcGeContext::gTol.equalPoint())
  95.   {
  96.     AcDbPolyline *p = new AcDbPolyline();
  97.     p->setDatabaseDefaults();
  98.     AcDbObjectId idFirst = ids[0];
  99.     AcGePoint3d nextPt = AcGePoint3d::kOrigin;
  100.     AcGePoint3d prevPt = AcGePoint3d::kOrigin;
  101.   
  102.     AcDbObjectPointer<AcDbCurve> c(idFirst,AcDb::kForRead);
  103.     if (c.openStatus() == Acad::eOk) {
  104.       AcGePoint3d ptStart, ptEnd;
  105.       c->getStartPoint(ptStart); c->getEndPoint(ptEnd);
  106.       p->addVertexAt(0, asPnt2d(asDblArray(ptStart)), BulgeFromArc(c, false), 0, 0);
  107.       p->addVertexAt(1, asPnt2d(asDblArray(ptEnd)), 0, 0, 0);
  108.       nextPt = ptEnd;
  109.       prevPt = ptStart;
  110.     }
  111.   
  112.     ids.remove(idFirst);
  113.     int prevCnt = ids.length() + 1;
  114.   
  115.     while (ids.length() > 0 && ids.length() < prevCnt)
  116.     {
  117.       prevCnt = ids.length();
  118.       for (int i = 0; i < ids.length(); i++) {
  119.         AcDbObjectId id = ids[i];
  120.         AcDbObjectPointer<AcDbCurve> cv(id,AcDb::kForRead);
  121.         if (cv.openStatus() == Acad::eOk) {
  122.           AcGePoint3d ptStart, ptEnd;
  123.           cv->getStartPoint(ptStart); cv->getEndPoint(ptEnd);
  124.           if (ptStart.distanceTo(nextPt) < FUZZ || ptEnd.distanceTo(nextPt) < FUZZ) {
  125.             double bulge = BulgeFromArc(cv, ptEnd.distanceTo(nextPt) < FUZZ);
  126.             p->setBulgeAt(p->numVerts() - 1, bulge);
  127.             if (ptStart.distanceTo(nextPt) < FUZZ)
  128.               nextPt = ptEnd;
  129.             else
  130.               nextPt = ptStart;
  131.             p->addVertexAt(p->numVerts(), asPnt2d(asDblArray(nextPt)), 0, 0, 0);
  132.             ids.remove(id);
  133.             break;
  134.           } else if (ptStart.distanceTo(prevPt) < FUZZ || ptEnd.distanceTo(prevPt) < FUZZ) {
  135.             double bulge = BulgeFromArc(cv, ptStart.distanceTo(prevPt) < FUZZ);
  136.             if (ptStart.distanceTo(prevPt) < FUZZ)
  137.               prevPt = ptEnd;
  138.             else
  139.               prevPt = ptStart;
  140.             p->addVertexAt(0, asPnt2d(asDblArray(prevPt)), bulge, 0, 0);
  141.             ids.remove(id);
  142.             break;
  143.           }
  144.         }
  145.       }
  146.     }
  147.     if (p->numVerts() == 0) {
  148.       delete p;  return NULL;
  149.     }  else  {
  150.       return p;
  151.     }
  152.   }
  153.   
  154.   /// <summary>
  155.   /// Getting bulge of curve
  156.   /// </summary>
  157.   /// <param name="c">AcDbCurve pointer</param>
  158.   /// <param name="clockwise">direction.</param>
  159.   /// <returns></returns>
  160.   static double BulgeFromArc(AcDbCurve *c, bool clockwise)
  161.   {
  162.     double bulge = 0.0;
  163.     AcDbArc *a = AcDbArc::cast(c);
  164.     if (a == NULL) return bulge;
  165.   
  166.     double newStart =
  167.       (a->startAngle() > a->endAngle()) ?
  168.       (a->startAngle() - 8 * atan(1.0)) :
  169.       (a->startAngle());
  170.   
  171.     bulge = tan((a->endAngle() - newStart) / 4.0);
  172.     if (clockwise) bulge = -bulge;
  173.     return bulge;
  174.   }
  175. } ;
  176.   
复制代码
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

Archiver|手机版|小黑屋|膜结构网

GMT+8, 2024-12-28 14:15 , Processed in 0.143702 second(s), 20 queries .

Powered by Discuz! X3.5

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表