ObjectARX 응용프로그램 기초


ObjectARX 응용프로그램 만들기


 












ObjectARX 응용프로그램 만들기
 
 

ObjectARX 응용프로그램은 AutoCAD의 주소 공간을 공유하고 AutoCAD 함수를 직접 호출하는 DLL입니다. ObjectARX 응용프로그램은 일반적으로 AutoCAD 내부에서 액세스가 가능하도록 한 명령 도구입니다. 이러한 명령들은 가끔 사용자 클래스를 사용하여 만들어집니다. ObjectARX 응용프로그램을 만드는 것은 다음과 같은 일반적인 절차를 포함합니다.

  ObjectARX 응용프로그램을 만들기 위해서는

  1. 새로운 명령들을 도구화하기 위하여 사용자 클래스들을 만듭니다.

      대부분의 ObjectARX 계층구조와 기호 테이블 클래스로부터 사용자 클래스를 파생할 수 있습니다.

  2. ObjectARX 응용프로그램이 처리하게 될 AutoCAD 메시지가 어떤 것인지를 결정합니다.

      AutoCAD는 AutoCAD 내부에서 발생하는 특정 이벤트를 표시하는 여러가지 메시지를 ObjectARX 응       용프로그램에게 보냅니다. 응용프로그램이 응답하게 될 메시지를 결정하면 그 메시지에 대한 실행       이 시작될 것입니다.

  3. AutoCAD에 대한 엔트리 포인트를 구성합니다.

      AutoCAD는 C++ 프로그램의 main() 함수에 해당하는 acrxEntryPoint() 함수를 통하여       ObjectARX 응용프로그램안에서 호출됩니다. 응용프로그램 내부에서 반드시 acrxEntryPoint()       함수를 도구화하여야 합니다. acrxEntryPoint() 함수는 특정 AutoCAD 메시지와 관련된 함수를       호출합니다.

  4. 초기화를 실행합니다.

      ObjectARX 응용프로그램 내부에서 생성했던 사용자 클래스를 초기화하여야 하고 ObjectARX 런타       임 클래스 트리를 다시 만듭니다. 그 밖에도 명령을 추가하기를 원한다면 AutoCAD에 그들을 등록해       야 합니다.

  5. 내리기를 준비합니다.

      ObjectARX 응용프로그램을 제대로 만들기 위해서는 응용프로그램이 내려질 때 일부 사용자 클래스       와 명령을 제거해야 합니다.


 












사용자 클래스 만들기
 
 

대부분의 ObjectARX 계층구조와 기호 테이블 클래스로부터 사용자 클래스를 파생할 수 있습니다. 이것은 자기 소유의 객체를 생성할 때 ObjectARX 클래스의 기능적인 수단을 허용해줍니다.

ObjectARX는 AcRxObject로부터 파생된 새로운 클래스를 생성하는데 도움이 되는 rxboiler.h  파일에 선언된 매크로들의 세트를 제공합니다. AutoCAD 릴리즈 12 엔티티 세트와 기호 테이블 클래스들을 제외한 ObjectARX 계층구조에 있는 대부분의 클래스로부터 새로운 클래스를 파생할 수 있습니다. 만일 새로운 클래스를 정의하기 위하여 ObjectARX 매크로들을 사용하지 않는다면, 클래스는 등록된 ObjectARX의 최상위 부모 클래스의 런타임을 동일하게 상속하게 될 것입니다.

응용프로그램은 다음과 같은 클래스로부터 새로운 클래스를 가장 효과적으로 파생할 수 있습니다.

    – AcRxObject
    – AcRxService
    – AcDbObject
    – AcDbEntity
    – AcDbCurve
    – AcDbObjectReactor
    – AcDbDatabaseReactor
    – AcDbEntityReactor
    – 모든 AcDbXxxDimension 클래스들
    – AcTransactionReactor
    – AcEdJig
    – AcEditorReactor

응용프로그램은 다음과 같은 클래스로부터는 클래스를 상속할 수 없습니다.

    – AcDbDimension
    – AcDbSymbolTable로부터 파생된 모든 클래스
    – AcDbBlockBegin
    – AcDbBlockEnd
    – AcDbSequenceEnd
    – AcDb2dPolyline
    – AcDb2dVertex
    – AcDb3dPolyline
    – AcDb3dPolylineVertex
    – AcDbPolygonMesh
    – AcDbPolygonMeshVertex
    – AcDbPolyFaceMesh
    – AcDbPolyFaceMeshVertex
    – AcDbFaceRecord
    – AcDbViewport
    – AcDbMInsertBlock
    – AcDbVertex

위의 리스트에 표시하지 않은 클래스는 이론상으론 파생될 수 있지만 완전히 확실하지는 않습니다.


 























































AutoCAD 메시지에 응답하기
 
 

AutoCAD가 ObjectARX 응용프로그램에 보내는 메시지에는 4가지 종류가 있습니다.

    – 모든 응용프로그램에게 보내는 메시지
    – 응용프로그램이 acedDefun() 함수에 의한 AutoLISP 함수로 등록되었을 때만 보내는 메시지
    – ObjectARX로서 서비스를 등록한 응용프로그램에게 보내는 메시지
    – ActiveX 자동화를 사용한 응용프로그램에 의해서만 응답되는 메시지

  모든 응용프로그램에게 보내는 메시지

 






















메시지 설            명
kInitAppMsg   ObjectARX 응용프로그램이 AutoCAD와 응용프로그램 사이의 통신을
  위해 올리기 되었을 때 보내집니다.
kUnloadAppMsg   ObjectARX 응용프로그램이 내리기 되었을 때, 즉 사용자가 응용프로그   램을 내리기 하였거나 AutoCAD가 종료되었을 때 보내집니다. 파일이 닫   혀지고 클린업 동작이 수행됩니다.
kLoadDwgMsg   도면이 열기 되었을 때 보내집니다. 응용프로그램이 AutoLISP의 함수로   등록되었다면 AutoCAD는 편집기안에 올려진 각각의 도면에 대해 이 메   시지를 보냅니다. AutoCAD 편집기는 이 시점에서 완전히 초기화되고 모   든 전역 함수는 사용가능하게 됩니다. 그러나 kLordDwgMsg 메시지로   부터 acedCommand() 함수를 사용할 수는 없습니다.
kSaveMsg   SAVE, SAVEAS, NEW, OPEN 명령이 실행되어 AutoCAD가 도면을
  저장할 때 보내집니다.
kUnloadDwgMsg   사용자가 도면 세션을 종료할 때 보내집니다.
kPreQuitMsg   AutoCAD가 종료될 때 보내지고, 모든 ObjectARX 응용프로그램을 내리   기 시작합니다.
 
 

  응용프로그램이 AutoLISP 함수로 등록되었을 때만 보내는 메시지

 
















메시지 설            명
kInvkSubrMsg   acedDefun() 함수를 사용하여 등록된 함수가 실행될 때 보내집니다.
kEndMsg   END 명령이 실행되고 저장될 필요가 있는 변경사항이 있을 때에만
  (dbmod!=0일 때) 보내집니다. kEndMsg 메시지는 NEW 또는 OPEN
  명령이 실행될 때는 보내지지 않고 대신에 kSaveMsg와 kLordDwgMsg   가 보내집니다. END 명령이 실행되고 dbmod = 0 이면 kEndMsg 메시   지 대신에 kQuitMsg 메시지가 보내집니다.
kQuitMsg   QUIT 명령이 실행되어 AutoCAD가 종료(저장없이 종료)될 때 보내집니   다. 또한 kQuitMsg 메시지는 위에 언급된 것처럼 END 명령이 실행되고   dbmod = 0 이면 보내집니다.
kCfgMsg   AutoCAD는 환경설정 프로그램으로부터 리턴될 때 보내지고 디스플레이   드라이버가 변경될 때만 사용됩니다.
 
 

  ObjectARX로서 서비스를 등록한 응용프로그램에게 보내는 메시지

 










메시지 설            명
kDependencyMsg   ObjectARX 응용프로그램이 AcRxService 객체로서 등록되고 서비스
  종속 카운터가 0에서 1로 변경될 때 보내집니다.
kNoDependencyMsg   ObjectARX 응용프로그램이 AcRxService 객체로서 등록되고 서비스
  종속 카운터가 1에서 0으로 변경될 때 보내집니다.
 
 

  ActiveX 자동화를 사용한 응용프로그램에 의해서만 응답되는 메시지

 







메시지 설            명
kOleUnloadAppMsg   응용프로그램이 내려질 수 있는 경우에만 보내집니다. 즉, 응용프로그램   의 ActiveX 객체나 인터페이스가 다른 응용프로그램에 의해 참조되지 않   는 경우에만 보내집니다.
 
 

AppMsgCode 형식 선언에 의해 정의되는 이러한 상수들은 rxdefs.h  파일을 참조하십시오.

ObjectARX 응용프로그램이 응답해야 할 메시지들을 결정할 필요가 있을 것입니다. 아래의 표는 받게된 메시지에 따라 권장되는 동작을 간단히 설명합니다.

 


































메시지 권장되는 동작
kInitAppMsg   서비스, 클래스, AcEd 명령 및 리액터, AcRxDynamicLinker 리액터를   등록합니다. 장치와 윈도우 같은 응용프로그램 시스템 자원을 초기화합   니다. 처음에 초기화 작업을 한꺼번에 모두 수행합니다. AcRx, AcEd,   AcGe 라이브러리 클래스들은 모두 사용할 수 있습니다. 응용프로그램을   잠금 해제 또는 재잠금하기를 원한다면 pkt 값을 저장합니다.
  장치 드라이버가 초기화되거나, 어떤 사용자 인터페이스 자원이 사용가   능하게 되거나, 응용프로그램이 특정 순서에 따라 올려지거나, AutoLISP   이 주어지거나 또는 데이터베이스가 열기되는 것들을 예상하지 마십시   오. 이러한 사항과 관련된 호출은 오류를 일으키며 때로는 치명적인 오류   가 될 것입니다. 일반적으로 AcDb와 AcGi 라이브러리는 관련된 AcRx   라이브러리와 다른 구조체가 적절할지라도 사용할 수 없습니다.
kUnloadAppMsg   최종 시스템 자원의 클린업을 수행합니다. kInitAppMsg 메시지에서
  시작되거나 생성된 어떤 것이든지 정지하거나 소멸시켜야 합니다.
  kInitAppMsg에서 설명된 것과 다른 차이점을 기대하지 마십시오.
  AutoCAD는 kInitAppMsg 실행시에 사용가능하게된 라이브러리 목록을
  제외하고는 이 호출이 이루어진 시점에서 대부분 해제될 수 있습니다.
kOleUnloadAppMsg   이 메시지는 ActiveX 자동화를 사용한 응용프로그램에서만 응답해야 합   니다.
  응용프로그램이 내려질 수 있다면 AcRx::kRetOK로 응답합니다. 내려질   수 없다면 AcRx::kRetError로 응답합니다.
kLoadDwgMsg   현재 도면 편집 세션에 관련된 초기화를 실행합니다. AcDb, AcGi 및 사   용자 인터페이스 API는 이제 모두 활성화됩니다. AutoCAD가 제공하는   모든 API들을 사용할 수 있습니다. 이 시점에서 등록된 AutoLISP 함수들   을 실행할 수 있고, 사용자 인터페이스를 초기화할 수 있습니다. 이제 수   행할 다른 동작은 AutoCAD 드라이버를 선택하고, acdbHostApplication
  Services()->workingDatabase()를 가장 초기에 액세스 가능하길 원한   다면 AcEditorReactor 이벤트를 질의하는 것을 포함합니다.
  모든 도면 편집 세션에서 발생하길 바라지 않는 어떤 것도 하면 안됩니   다. 이 메시지가 프로그램 실행당 한번 이상 보내졌다고 가정합니다.
kUnloadDwgMsg   kLoadDwgMsg 코드 응답시에 시작되거나 등록된 모든 것을 해제하거
  나 클린업합니다. 지속되는 리액터를 제외하고 모든 AcDb 리액터를 해   제합니다.
  편집 세션에 연결되지 않은 시스템 자원들 또는 AcRx 클래스, AcEd 리   액터 또는 명령들을 삭제하지 마십시오. 이것들은 편집 세션 동안 유효한   상태로 남아 있습니다.
kDependencyMsg   응용프로그램이 내려질 수 없도록 잠금 처리를 하는 것과 같이 어떤
  다른 응용프로그램이 이것에 독립적이될 때 응용프로그램에 필요한
  작업을 수행합니다.
kNoDependencyMsg   필요하다면 사용자가 응용프로그램을 내릴 수 있도록 잠금 해제를 하는   것과 같이 어떤 다른 응용프로그램이 이것에 독립적인 것이 더이상 없을   때 응용프로그램에 필요한 작업을 수행합니다.
kInvkSubrMsg   acedDefun()과 함께 등록된 함수들을 실행합니다.
  acedGetFuncode()의 호출을 만듦으로서 함수를 결정합니다.
  acedRetxxx() 함수를 사용하여 값을 리턴합니다.
kPreQuitMsg   응용프로그램이 종료되기 전에 부속 프로그램이 내려지는 것을 보증하
  도록 응용프로그램을 제어하도록 독립적인 것들(응용프로그램, DLL 등)   을 내립니다.
kEndMsg
kCfgMsg
kQuitMsg
kSaveMsg
  이같은 메시지들에 응답하기 위해 선택적으로 AcEditorReactor 이벤트   콜백을 사용하는 것을 고려합니다.
  AcEditorReactor를 통해 만들어진 동등한 이벤트 콜백에 응답하고 있다   면 이같은 메시지들에 응답하지 않습니다.
 
 

AutoCAD가 ObjectARX 응용프로그램 사이의 메시지 전달 처리는 AutoCAD로부터 ObjectARX 응용프로그램으로 한 방향으로 이루어집니다. 아래의 그림은 메시지 전달의 전형적인 절차를 보여줍니다.

          


 












AutoCAD에 대한 엔트리 포인트 만들기
 
 

AutoCAD는 C++ 프로그램의 main() 함수에 해당하는 acrxEntryPoint()를 통해 ObjectARX 모듈을 호출합니다. 따라서 acrxEntryPoint() 함수를 도구화해야 합니다.

acrxEntryPoint() 함수는 ObjectARX 응용프로그램과 통신하기 위해 AutoCAD에 대한 엔트리 포인트를 제공합니다. ObjectARX 응용프로그램은 상태 코드를 리턴함으로서 AutoCAD와 통신할 수 있습니다. acedDefun() 함수로 정의된 함수를 실행하는 모든 요구는 acrxEntryPoint() 함수에서 만듭니다. ObjectARX 또는 acedRegFunc() 함수로 새로운 명령을 정의하면 AutoCAD는 명령과 관련된 함수를 즉시 실행합니다.

acrxEntryPoint() 함수는 다음과 같은 형식을 갖습니다.

        extern “C”
        AcRx::AppRetCode
        acrxEntryPoint(AcRx::AppMsgCode msg, void* pkt);

  msg
        ObjectARX 커널로부터 응용프로그램에게 보내진 메시지를 표현합니다.

  pkt
        패킷 데이터 값을 저장합니다.

  AppRetCode
        AutoCAD에 리턴되는 상태 코드를 저장합니다.

acrxEntryPoint() 함수의 정의 내부에서 AutoCAD로부터 보내진 메시지를 해독하기 위해 switch 구문이나 이와 유사한 코드를 사용하고, 각각의 메시지에 관련된 적절한 작업을 수행하며 상태값을 정수로 리턴합니다.

참 고 : acrxEntryPoint() 함수로부터 리턴되는 마지막 값이 kRetError이면 kOleUnloadAppMsg와             kUnloadAppMsg 메시지를 제외하고 응용프로그램이 내려지게되는 원인이 될 것입니다.

다음 코드는 올바른 switch 구문의 형식을 보여줍니다.

        AcRx::AppRetCode
        acrxEntryPoint(AcRx::AppMsgCode msg, void* pkt)
        {
            switch(msg) {
                case AcRx::kInitAppMsg:
                    break;
                case AcRx::kUnloadAppMsg:
                    break;
                …
                default:
                    break;
            }
            return AcRx::kRetOK;
        }


 












ObjectARX 응용프로그램 초기화하기
 
 

응용프로그램에서 정의한 사용자 클래스와 명령을 초기화해야 합니다. 이 초기화는 acrxEntryPoint() 함수내의 AcRx::kInitAppMsg 경우에 위치하거나 또는 그 경우에 호출된 함수에 위치할 수 있습니다.

  ObjectARX 응용프로그램을 초기화하려면

  1. 사용자 클래스를 정의했다면 rxInit() 함수를 실행합니다.

  2. 사용자 클래스를 정의했다면 ObjectARX 런타임 클래스 트리를 재생성하기 위하여 acrxBuild
      ClassHierarchy() 함수를 호출합니다.

      효율을 위해 사용자 클래스 각각에 대해 rxInit() 함수를 호출한 후에 acrxBuildClass
      Hierarchy() 함수를 호출합니다.

  3. 필요한 다른 초기화 작업을 수행합니다.

  4. 서비스 이름을 등록합니다.

      서비스 이름을 등록하는 것은 다른 응용프로그램이 응용프로그램에 종속될 때 필요합니다. 서비스       이름을 등록하는 것은 다른 응용프로그램이 서비스에 종속되어 등록되는 것을 허용하며, 응용프로       그램이 내려지기 전에 어떤 것이 종속관계에 있는지를 검사할 수 있게 합니다. 또한 응용프로그램을       위한 서비스 이름을 등록하는 것은 ObjectARX 메커니즘을 사용한 응용프로그램으로부터 특정 함수       를 추출할 경우 필요하게 됩니다. acrxRegisterService() 함수 또는 AcRxService 클래스를 사       용할 수 있습니다.

  5. AutoCAD 명령 메커니즘에 따라 명령을 등록합니다.

      응용프로그램에서 정의한 명령을 AutoCAD에서 동작하게 하려면 acedRegCmds->add
      Command() 함수를 사용합니다.


 












내리기를 위한 준비
 
 

응용프로그램을 내릴 때에는 응용프로그램에서 생성했던 사용자 클래스와 명령을 클린업해야 합니다. 이 내용은 acrxEntryPoint() 함수내의 AcRx::kUnloadAppMsg 경우에 위치하거나 또는 그 경우에 호출된 함수에 위치할 수 있습니다.

  ObjectARX 응용프로그램을 내리기하려면

  1. acedRegCmds 매크로 또는 acedDefun() 함수로서 명령을 생성했다면 그것들을 제거합니다.

      일반적으로 ObjectARX 명령들은 acedRegCmds->removeGroup() 함수를 사용하여 그룹에       의해 삭제됩니다.

  2. 사용자 클래스를 생성하였다면 그것들을 삭제합니다.

      AcRx 런타임 트리에서 사용자 클래스를 삭제하려면 deleteAcRxClass() 함수를 사용합니다. 클       래스는 먼저 파생된 클래스의 가지부터 시작하여 제거되어야 하며, 부모 클래스의 클래스 트리 순으       로 삭제합니다.

  3. 응용프로그램에 의해 추가된 객체를 삭제합니다.

      데이터베이스에 현재 상주하는 AcDbObject 인스턴스에 대하여 무시하는 것을 AutoCAD에 전달할       방법은 없습니다. 그러나 응용프로그램이 내려지게 될 때 AutoCAD는 그러한 객체들을 자동적으로       AcDbProxyObject나 AcDbProxyEntity로 변환하게 될 것입니다.

  4. AcDbObject, AcDbDatabase, AcRxDynamicLinker 또는 AcEditor 객체에 부착된 리액터를 삭제합       니다. 단, AcDbObjects의 영구적인 리액터는 예외입니다. 이것들은 응용프로그램이 내려지게 될 때       프록시 객체로 변환될 것입니다.

  5. 서비스 이름을 생성하였다면 이것을 삭제합니다.

      응용프로그램에 등록된 어떤 서비스를 삭제하기 위해서는 acrxServiceDictionary->remove()       함수를 사용할 수 있습니다.


 












예제 코드
 
 

아래의 예제 응용프로그램은 응용프로그램이 올려지고 내려질 때 호출되는 함수들을 도구화합니다. 이것의 초기화 함수는 두 개의 새로운 함수 CREATEITERATE를 추가합니다. 또한 이것은 새로운 클래스 AsdkMyClass를 초기화하고 acrxBuildClassHierarchy() 함수를 사용하여 ObjectARX 계층구조에 이 클래스를 추가합니다.

        // kInitAppMsg 메시지를 받은 경우 acrxEntryPoint() 함수로부터 호출되는 초기화 함수
        // 명령 스택에 명령을 추가하고 ACRX 클래스 계층구조에 클래스를 추가하기 위하여 사용됩니다.
        //
        void
        initApp()
        {
            acedRegCmds->addCommand(“ASDK_DICTIONARY_COMMANDS”,
                    “ASDK_CREATE”, “CREATE”, ACRX_CMD_MODAL, createDictionary);
            acedRegCmds->addCommand(“ASDK_DICTIONARY_COMMANDS”,
                    “ASDK_ITERATE”, “ITERATE”, ACRX_CMD_MODAL, iterateDictionary);
            AsdkMyClass::rxInit();
            acrxBuildClassHierarchy();
        }

        // kUnloadAppMsg 메시지를 받은 경우 acrxEntryPoint() 함수로부터 호출되는 클린업 함수
        // 명령 스택에서 명령을 삭제하고 ACRX 클래스 계층구조에서 사용자 클래스를 삭제합니다.
        //
        void
        unloadApp()
        {
            acedRegCmds->removeGroup(“ASDK_DICTIONARY_COMMANDS”);

            // ACRX 런타임 클래스 계층구조에서 AsdkMyClass 클래스를 삭제합니다.
            // 만일 이것이 데이터베이스가 활성화되어 있는 동안 실행되면,
            // AsdkMyClass 클래스의 모든 객체들을 프록시 객체로 변환하게 될 것입니다.
            //
            deleteAcRxClass(AsdkMyClass::desc());
        }


 












새로운 명령 등록하기
 
 

AutoCAD 명령들은 AcEdCommandStack 클래스에 의해 정의된 명령 스택에 저장됩니다. 명령 스택의 인스턴스는 AutoCAD 세션당 하나의 인스턴스가 생성됩니다. 이 스택은 사용자가 정의한 명령들로 구성됩니다. acedRegCmds() 매크로는 명령 스택을 액세스하게 합니다.

명령을 추가할 때 또한 명령의 그룹명을 설정합니다. 다른 명령과 이름 중복을 피하기 위한 좋은 방법은 그룹 이름을 등록한 개발자 접두어를 사용하는 것입니다. 주어진 그룹내의 명령 이름들은 유일해야 하며 그룹 이름도 유일해야 합니다. 그러나 다중 응용프로그램에서 그룹명은 명백한 명령을 만들기 때문에 같은 이름의 명령을 추가할 수 있습니다.

참 고 : Autodesk는 서로 다른 응용프로그램간의 이름의 중복을 피하기 위하여 개발자 스키마 등록을 제           공합니다. 등록된 각각의 개발자는 명시적인 사용을 위해 하나 이상의 등록된 개발자 기호(RDS)           를 선택합니다. 등록된 개발자 기호는 “Built with ObjectARX” 로고 프로그램의 필요조건 중의 하           나입니다.

일반적으로 AcEdCommandStack::addCommand() 함수를 사용하여 한 번에 명령들을 추가하고, AcEdCommandStack::removeGroup() 함수를 사용하여 그룹을 통해 명령들을 제거합니다. 또한 한 번에 하나씩 명령을 제거하기 위해서 AcEdCommandStack::removeCmd() 함수를 사용할 수도 있습니다. 응용프로그램은 클린업의 일부로서 등록된 일부 명령을 제거하는 것이 필요합니다.

addCommand() 함수의 형식은 다음과 같습니다.

        Acad::ErrorStatus
        addCommand(
            const char* cmdGroupName,
            const char* cmdGlobalName,
            const char* cmdLocalName,
            Adesk::Int32 commandFlags,
            AcRxFunctionPtr functionAddr,
            AcEdUIContext *UIContext = NULL,
            int fcode=-1,
            HINSTANCE hResourceHandle = NULL,
            AcEdCommand** cmdPtrRet = NULL);

  cmdGroupName
        명령을 추가하기 위한 그룹명을 ASCII 형태로 표시합니다. 그룹이 존재하지 않으면 명령이 추가되         기 전에 생성됩니다.

  cmdGlobalName
        추가할 명령 이름을 ASCII 형태로 표시합니다. 이 이름은 전역 또는 번역되지 않은 이름으로 불립         니다.

  cmdLocalName
        추가할 명령 이름을 ASCII 형태로 표시합니다. 이 이름은 지역 또는 번역된 이름으로 불립니다.

  commandFlags
        명령과 함께 조합된 플래그입니다. 유효한 값은 ACRX_CMD_TRANSPARENT, ACRX_CMD_         MODAL, ACRX_CMD_USEPICKSET 및 ACRX_CMD_REDRAW 입니다.

  functionAddr
        AutoCAD에 의해 이 명령이 실행될 때 실행될 함수의 주소입니다.

  UiContext
        AcEdUIContext 콜백 클래스를 위한 입력 포인터입니다.

  fcode
        명령을 위해 설정된 정수 코드입니다.

  hResourceHandle
        명령이 실행될 때 현재로 만들기 위한 자원 핸들입니다.

  cmdPtrRet
        명령을 추가하기 위한 AcEdCommand 객체의 주소 포인터입니다.

참 고 : 모든 명령 이름들은 다른 응용프로그램과 이름의 중복을 피하기 위하여 등록된 4개 문자의 개발            자 접두어를 사용할 것을 강력하게 권고합니다. 예를 들어 ASDK인 개발자의 MOVE 명령어는            ASDKMOVE로 지정하십시오. 그룹명 또한 등록된 개발자 접두어를 사용할 것을 권장합니다.

removeCmd() 함수의 형식은 다음과 같습니다.

        virtual Acad::ErrorStatus
        AcEdCommandStack::removeCmd
            (const char* cmdGroupName, const char* cmdGlobalName) = 0;

removeGroup() 함수의 형식은 다음과 같습니다.

        virtual Acad::ErrorStatus
        AcEdCommandStack::removeGroup
            (const char* groupName);

명령 스택은 명령이 실행될 때 그룹명에 의해 검색된 후 그룹내의 명령 이름에 의해 검색됩니다. 일반적으로 첫 번째로 등록된 그룹은 가장 먼저 검색되겠지만 항상 이 순서로 검색된다는 보장은 없습니다. 특정 그룹이 먼저 검색되도록 지정하기 위해서는 AcEdCommandStack::popGroupToTop() 함수를 사용합니다. 사용자 수준에서 ARX 명령의 Group 옵션은 처음에 검색될 그룹을 지정하는 것을 허용합니다.

AutoCAD에 명령을 추가할 때 어떤 언어로 사용될 수 있을 것인가 하는 전역 이름과 외국어 버전에서 사용되어질 명령 이름의 번역된 이름인 지역 이름 모두를 지정할 필요가 있습니다. 물론 지역 언어로 명령을 번역할 필요가 없다면 전역 이름과 지역 이름 모두를 동일하게 사용하면 됩니다.

명령은 투명이나 모달로 사용할 수 있습니다. 투명 명령은 사용자가 입력을 위해 일시정지한 상태에서도 실행될 수 있습니다. 모달 명령은 AutoCAD가 명령 프롬프트를 전달하고 다른 명령이나 프로그램이 현재 실행되지 않을 때에만 실행될 수 있습니다. AcEdCommandStack::addCommand() 함수에서 commandFlags 인수는 새로운 명령이 모달(ACRX_CMD_MODAL)인지 투명(ACRX_CMD_ TRANSPARENT)인지를 지정합니다. 또한 commandFlags 인수는 명령을 위한 다른 옵션들을 지정합니다. 투명 명령은 한 개의 레벨로만 중첩될 수 있습니다. 즉, 주 명령이 실행된 상태에서 단 하나의 투명 명령만이 실행될 수 있습니다.

전역 객체의 공통 세트를 조작하는 다중 명령을 생성한다면 다른 명령에 의해 방해받지 않도록 하기 위하여 모달 명령으로 만들어야 하는지를 고려하십시오. 이러한 충돌이 문제가 되지 않는다면 새로운 명령을 투명 명령으로 만드는 것은 사용상의 많은 유연성을 부여하게 됩니다.


 






































ObjectARX 응용프로그램 올리기
 
 

다음과 같은 방법들을 사용하여 ObjectARX 응용프로그램을 올릴 수 있습니다.

       응용프로그램을 AutoCAD에 의해 올리기 요구를 허용하는 기능을 갖도록 준비합니다. 이 기능은       Windows NT 또는 Windows 95 시스템 레지스트리내의 특정 응용프로그램 전체를 포함합니다.
       초기 모듈 파일 acad.rx 내에 응용프로그램을 지정합니다. 이 파일은 AutoCAD가 시작될 때 올려       야 할 모든 프로그램의 이름을 ASCII 문자로 담고 있습니다. 파일의 각 행은 프로그램 이름을 담고       있습니다. 만일 파일이 AutoCAD 라이브러리 탐색 경로상에 없다면 경로를 포함합니다. acad.rx        파일은 반드시 AutoCAD 라이브러리 탐색 경로상의 디렉토리에 있어야만 합니다.
       AcRxDynamicLinker::loadModule() 함수를 사용하여 또다른 ObjectARX 응용프로그램으       로부터 응용프로그램 올리기 요구를 만듭니다.
       AutoCAD 보너스 프로그램 loadapp.arx 내에 정의된 APPLOAD 대화상자를 사용합니다.
       AutoLISP에서 arxload() 함수를 사용합니다.
       ObjectARX에서 acedArxLoad() 함수를 사용합니다.
       AutoCAD 명령행에서 ARX 명령을 입력하고 Load 옵션을 사용합니다.
 
 

arxload() 같은 올리기 기능은 탐색 경로를 지정하지 않으면 AutoCAD 라이브러리 탐색 경로에 의해 지정된 디렉토리에서 응용프로그램을 검색합니다. AutoCAD 라이브러리 탐색 경로는 다음과 같은 순서로 검색합니다.

    1. 현재 디렉토리
    2. 현재 도면 파일이 있는 디렉토리
    3. 지원 경로에 의해 지정된 디렉토리
    4. AutoCAD 프로그램 파일을 포함하고 있는 디렉토리

현재 올려진 모든 ObjectARX 프로그램 이름을 검색하기 위해서는 ARX 명령의 Commands 옵션을 사용하면 됩니다. 또한 AutoCAD 보너스 프로그램 loadapp.arx 내에 정의된 APPLOAD 대화상자에서 현재 올려진 ObjectARX 프로그램 이름 목록을 볼 수 있습니다.


 
































ObjectARX 응용프로그램 내리기
 
 

다음과 같은 방법들을 사용하여 잠금 처리되지 않은 ObjectARX 응용프로그램을 내릴 수 있습니다.

       AcRxDynamicLinker::unloadModule() 함수를 사용하여 또다른 ObjectARX 응용프로그램       으로부터 응용프로그램 내리기 요구를 만듭니다.
       AutoCAD 보너스 프로그램 loadapp.arx 내에 정의된 APPLOAD 대화상자를 사용합니다. 이 파일       은 AutoLISP arxload()arxunload() 함수들을 위한 사용자 인터페이스를 정의합니다.
       AutoLISP에서 arxunload() 함수를 사용합니다.
       ObjectARX에서 acedArxUnload() 함수를 사용합니다.
       AutoCAD 명령행에서 ARX 명령을 입력하고 Unload 옵션을 사용합니다.
 
 

응용프로그램은 디폴트로 잠금처리되고, 내려질 수 없게 됩니다. 응용프로그램을 “내리기 가능”으로 분류하기 위해서는 응용프로그램이 AutoCAD와 다른 응용프로그램에 의해 자신의 어떤 객체 또는 구조체를 더 이상 참조하지 않는다는 것을 확신해야만 합니다. 응용프로그램을 내리기 가능으로 만들기 전에 응용프로그램의 주소 공간내에 어떤 객체의 활성화된 포인터를 담고 있는 예속 응용프로그램이 없는지에 주의를 기울여야 합니다. 클린업 조작을 수행할 응용프로그램들은 잠금해제가 수행되어야만 합니다.

응용프로그램을 잠금해제하려면 AcRx::kInitAppMsg 메시지가 전달될 때 pkt 인수의 값을 저장할 필요가 있습니다. pkt 인수는 unlockApplication() 함수에 의해 사용될 것입니다.

응용프로그램을 잠그거나 잠금해제하기 위해서는 다음의 두 함수를 사용합니다.

        bool
        AcRxDynamicLinker::lockApplication(void* pkt) const;

        bool
        AcRxDynamicLinker::unlockApplication(void* pkt) const;

아래의 함수는 응용프로그램이 잠겨있는지의 여부를 검사합니다.

        bool
        AcRxDynamicLinker::isApplicationLocked(const char* name) const;

또한 유사한 전역 함수들이 제공됩니다.

        bool
        acrxLockApplication(void* pkt);

        bool
        acrxUnlockApplication(void* pkt);

        bool
        acrxApplicationIsLocked(const char* modulename);


 


 


올리기 요구하기


 








































올리기 요구
 
 

올리기 요구는 AutoCAD에 올려져있지 않은 ObjectARX 응용프로그램을 자동으로 올리려는 기능입니다. ObjectARX 응용프로그램은 다음중 하나 이상의 환경에서 AutoCAD에 의해 올려질 수 있도록 설계될 수 있습니다.

       올려지지 않은 응용프로그램에 의해 만들어진 사용자 객체를 가지고 있는 도면 파일이 읽혀질 때
       사용자 또는 다른 응용프로그램이 올려지지 않은 응용프로그램의 명령중 하나를 실행할 때
       AutoCAD가 시작될 때
 
 

참 고 : AutoCAD가 시작될 때 올리기 요구가 이루어진 응용프로그램은 acad.rx  파일내의 목록들이 올려            지기 전에 올려집니다.

올리기 요구는 다음과 같은 장점을 제공하기 때문에 AutoCAD의 올리기 요구 기능을 최대한 활용하는 ObjectARX 응용프로그램을 개발할 것을 권장합니다.

       프록시 객체 생성의 제한
       보다 많은 유연성 제공
       메모리의 효율적인 사용
 
 

올리기 요구가 가능한 응용프로그램에서 응용프로그램의 사양 정보는 Windows 시스템 레지스트리에 저장되어야 합니다. 하나 이상의 DLL과 함께 실행되는 ObjectARX 응용프로그램은 다른 콤포넌트들을 모두 올려야 할 책임이 있는 “제어” 모듈이 필요하게 될지도 모릅니다. 마지막으로 DEMANDLOAD 시스템 변수는 올리기 요구를 위한 적절한 값으로 설정되어야 합니다.

참 고 : ObjectARX 응용프로그램은 네트워크 또는 인터넷 주소를 사용한 경로로부터 올리기가 가능합니            다.


 












AutoCAD, 윈도우즈 시스템 레지스트리 및 ObjectARX 응용프로그램
 
 

AutoCAD는 다른 AutoCAD 릴리즈, 언어 버전, AutoCAD Map과 같은 어떤 컴퓨터에 설치될지 모르는 제품을 유일하게 식별하는 정보를 포함하는 응용프로그램 정보의 전체 범위를 유지하기 위하여 Windows 시스템 레지스트리를 사용합니다. AutoCAD의 여러가지 버전을 식별하는 레지스트리 정보는 ObjectARX 개발자들에게 아주 중요한 것입니다. ObjectARX 응용프로그램을 위한 설치 프로그램은 그것이 실행될 AutoCAD 버전에 관한 정보와 함께 ObjectARX 응용프로그램에 관한 정보가 조합되어야 합니다.

AutoCAD 설치 프로그램은 시스템 레지스트리내 릴리즈 번호 키 바로 아래에 유일한 타임 스탬프를 생성합니다. 이 키는 같은 릴리즈의 서로 다른 AutoCAD의 다른 버전이 시스템 레지스트리의 그들 자신의 섹션을 다룰 수 있을 것이라는 것을 보증합니다. 이 키의 값들로는 아래와 같이 AutoCAD 파일의 위치, 언어 버전 및 제품 이름이 저장됩니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\R15.0\
            ACAD-1:409\
                …
                AcadLocation:REG_SZ:f:\ACAD2000
                Language:REG_SZ:English
                ProductName:REG_SZ:AutoCAD Map R15.0
            …

ObjectARX 응용프로그램의 설치 프로그램은 적절한 언어와 제품 값뿐만 아니라 적절한 AutoCAD 릴리즈 키의 위치도 알아내야 합니다.

또한 타임 스탬프 키는 현재 로드된 AutoCAD의 버전 또는 가장 최근에 실행된 버전을 식별하는데 사용됩니다. 이 식별은 AutoCAD가 실행될 때 레지스트리의 HKEY_CLASSES_ROOT 전역 섹션에 AutoCAD “현재” 버전 정보가 재설정되기 때문에 필요합니다.

레지스트리의 릴리즈 키 섹션의 CurVer 값은 현재 버전을 식별하기 위해 다음과 같이 사용됩니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\R15.0\
            …
            CurVer:REG_SZ:ACAD-1:409

AutoCAD가 ObjectARX 응용프로그램의 올리기 요구를 시도할 때, AutoCAD는 ObjectARX 응용프로그램에 대한 정보를 AutoCAD의 최종 릴리즈에 속하는 레지스트리 섹션에서 찾습니다. 만일 그곳에서 ObjectARX 정보를 찾을 수 없으면 AutoCAD의 이전 버전 섹션을 검사하고 정보가 발견되거나 AutoCAD 릴리즈 정보가 더 이상 없을 때까지 역순으로 계속 찾습니다.


 





















































올리기 요구
 
 

올리기 요구는 AutoCAD에 올려져있지 않은 ObjectARX 응용프로그램을 자동으로 올리려는 기능입니다. ObjectARX 응용프로그램은 다음중 하나 이상의 환경에서 AutoCAD에 의해 올려질 수 있도록 설계될 수 있습니다.

       올려지지 않은 응용프로그램에 의해 만들어진 사용자 객체를 가지고 있는 도면       파일이 읽혀질 때
       사용자 또는 다른 응용프로그램이 올려지지 않은 응용프로그램의 명령중 하나를       실행할 때
       AutoCAD가 시작될 때
 
 

참 고 : AutoCAD가 시작될 때 올리기 요구가 이루어진 응용프로그램은 acad.rx  파일            내의 목록들이 올려지기 전에 올려집니다.

올리기 요구는 다음과 같은 장점을 제공하기 때문에 AutoCAD의 올리기 요구 기능을 최대한 활용하는 ObjectARX 응용프로그램을 개발할 것을 권장합니다.

       프록시 객체 생성의 제한
       보다 많은 유연성 제공
       메모리의 효율적인 사용
 
 

올리기 요구가 가능한 응용프로그램에서 응용프로그램의 사양 정보는 Windows 시스템 레지스트리에 저장되어야 합니다. 하나 이상의 DLL과 함께 실행되는 ObjectARX 응용프로그램은 다른 콤포넌트들을 모두 올려야 할 책임이 있는 “제어” 모듈이 필요하게 될지도 모릅니다. 마지막으로 DEMANDLOAD 시스템 변수는 올리기 요구를 위한 적절한 값으로 설정되어야 합니다.

참 고 : ObjectARX 응용프로그램은 네트워크 또는 인터넷 주소를 사용한 경로로부터            올리기가 가능합니다.

AutoCAD, 시스템 레지스트리 및 ObjectARX 응용프로그램

AutoCAD는 다른 AutoCAD 릴리즈, 언어 버전, AutoCAD Map과 같은 어떤 컴퓨터에 설치될지 모르는 제품을 유일하게 식별하는 정보를 포함하는 응용프로그램 정보의 전체 범위를 유지하기 위하여 Windows 시스템 레지스트리를 사용합니다. AutoCAD의 여러가지 버전을 식별하는 레지스트리 정보는 ObjectARX 개발자들에게 아주 중요한 것입니다. ObjectARX 응용프로그램을 위한 설치 프로그램은 그것이 실행될 AutoCAD 버전에 관한 정보와 함께 ObjectARX 응용프로그램에 관한 정보가 조합되어야 합니다.

AutoCAD 설치 프로그램은 시스템 레지스트리내 릴리즈 번호 키 바로 아래에 유일한 타임 스탬프를 생성합니다. 이 키는 같은 릴리즈의 서로 다른 AutoCAD의 다른 버전이 시스템 레지스트리의 그들 자신의 섹션을 다룰 수 있을 것이라는 것을 보증합니다. 이 키의 값들로는 아래와 같이 AutoCAD 파일의 위치, 언어 버전 및 제품 이름이 저장됩니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\R15.0\
            ACAD-1:409\
                …
                AcadLocation:REG_SZ:f:\ACAD2000
                Language:REG_SZ:English
                ProductName:REG_SZ:AutoCAD Map R15.0
            …

ObjectARX 응용프로그램의 설치 프로그램은 적절한 언어와 제품 값뿐만 아니라 적절한 AutoCAD 릴리즈 키의 위치도 알아내야 합니다.

또한 타임 스탬프 키는 현재 로드된 AutoCAD의 버전 또는 가장 최근에 실행된 버전을 식별하는데 사용됩니다. 이 식별은 AutoCAD가 실행될 때 레지스트리의 HKEY_CLASSES_ROOT 전역 섹션에 AutoCAD “현재” 버전 정보가 재설정되기 때문에 필요합니다.

레지스트리의 릴리즈 키 섹션의 CurVer 값은 현재 버전을 식별하기 위해 다음과 같이 사용됩니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\R15.0\
            …
            CurVer:REG_SZ:ACAD-1:409

AutoCAD가 ObjectARX 응용프로그램의 올리기 요구를 시도할 때, AutoCAD는 ObjectARX 응용프로그램에 대한 정보를 AutoCAD의 최종 릴리즈에 속하는 레지스트리 섹션에서 찾습니다. 만일 그곳에서 ObjectARX 정보를 찾을 수 없으면 AutoCAD의 이전 버전 섹션을 검사하고 정보가 발견되거나 AutoCAD 릴리즈 정보가 더 이상 없을 때까지 역순으로 계속 찾습니다.

ObjectARX 응용프로그램 설치시 레지스트리 수정


AutoCAD는 올리기 요구에 대한 ObjectARX 응용프로그램의 위치를 지정하기 위하여 Windows NT 또는 Windows 95의 시스템 레지스트리를 사용합니다. 레이스트리의 AutoCAD 섹션의 한 부분은 ObjectARX 응용프로그램 레지스트리 정보 위치에 대한 정보로 사용됩니다.

ObjectARX 응용프로그램의 설치 프로그램은 올리기 요구를 원하는 시스템 레지스트리안에 특정 키와 값을 생성해야 합니다. 몇몇의 요구되는 키와 값은 레지스트리의 AutoCAD 섹션안에 생성되어야 하고 다른 것들은 ObjectARX 응용프로그램 섹션에 생성되어야 합니다.

ObjectARX 응용프로그램이 하나 이상의 AutoCAD 버전, 즉 다른 언어 버전이나 AutoCAD Map 같은 관련된 제품으로 실행되도록 설계되었다면 설치 프로그램은 AutoCAD 각각의 버전에 대한 레지스트리의 섹션에 적절한 정보를 추가해야 합니다.

ObjectARX 응용프로그램의 설치 과정에는 다음과 같은 내용이 포함되어야 합니다.

       AutoCAD의 적절한 버전에 대한 시스템 레지스트리의 섹션이 존재하는지 검증
      합니다. AutoCAD 섹션의 레지스트리가 존재하지 않으면 사용자는 AutoCAD의
      적합한 버전이 설치되지 않았다는 경고를 받게 되고 설치는 중단되어야 합니다.
       AutoCAD의 적합한 버전의 시스템 레지스트리의 섹션안에 응용프로그램에 대한       특정 키의 세트와 값을 생성합니다.
       또 다른 특정 키의 세트와 값들의 키 집합과 응용프로그램 자신의 주요 키를 생       성합니다.
 
 

예제 프로그램 polysamp 의 올리기 요구에 대한 시스템 레지스트리가 어떻게 수정되는지에 대한 정보는 ObjectARX SDK의 \objectarx\samples\polysamp\demandload  디렉토리를 참조하십시오. 설치 예제 프로그램은 ObjectARX SDK의 \objectarx\utils  디렉토리에 있습니다.

AutoCAD의 보조키 및 값 생성하기


ObjectARX 응용프로그램의 설치 프로그램은 실행되어야 할 응용프로그램과 함께 AutoCAD 각각의 버전의 시스템 레지스트리내의 섹션안에 응용프로그램에 대한 키의 세트와 값을 관리하도록 설계되어야 합니다. 아래의 예제는 응용프로그램이 생성하고 유지하여야 하는 레지스트리 섹션에서 키와 값의 배치를 보여줍니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\releaseNum\
           ACAD-1:LocaleID\
              Applications\
                 ApplicationName\
                    LoadCtrls:REG_DWORD:acrxAppLoadReason
                    RegPath:REG_SZ:RegistryPathWhereLoaderIsSpecified

releaseNum과 ACAD-1:LocaleID 키는 AutoCAD 설치 프로그램에 의해 생성됩니다.

ApplicationName 키는 프로그램을 식별하기 위해 AutoCAD에 의해 내부적으로 사용되는 응용프로그램의 논리적인 이름이어야 합니다.

acrxAppLoadReason 값은 각기 관련된 의미를 지닌 다음 16 진수 목록 값들중 하나 이상의 값을 논리적 OR 계산을 사용하여 올려질 응용프로그램의 상태를 정의합니다.

  0x01
        프록시 객체가 발견되면 응용프로그램을 올립니다.

  0x02
        AutoCAD가 시작되면 응용프로그램을 올립니다.

  0x04
        관련된 명령이 시작되면 응용프로그램을 올립니다.

  0x08
        사용자 또는 다른 응용프로그램에 의해 요구되면 응용프로그램을 올립니다.

  0x10
        응용프로그램을 올리지 않습니다.

RegistryPathWhereLoaderIsSpecified 값은 레지스트리의 응용프로그램 섹션에 대한 레지스트리 경로를 식별해야 합니다.

ObjectARX API에는 시스템 레지스트리의 AutoCAD 섹션안에 응용프로그램에 대한 정보를 입력하기 위해 ObjectARX 응용프로그램에서 사용될 수 있는 acrxRegisterApp() 함수가 있습니다. 일반적으로 acrxRegisterApp() 함수는 응용프로그램이 처음으로 올려지게될 때 정보를 입력하게 되고 다음에 올려질 때는 정보가 있는지 확인하게 됩니다.

ObjectARX 응용프로그램의 키 및 값 생성하기


ObjectARX 응용프로그램의 설치 프로그램은 시스템 레지스트리의 응용프로그램 섹션을 관리하도록 설계되어야 합니다. 레지스트리의 이 섹션은 응용프로그램의 핵심 모듈과 응용프로그램의 명령 세트를 식별하는 키와 값을 가져야 합니다.

Loader 키내의 값은 AutoCAD가 먼저 올려야할 모듈의 경로와 파일 이름을 가져야 합니다. 올리기를 위한 모듈은 응용프로그램을 구성하는 어떤 다른 모듈을 순차적으로 올려야할 책임이 있습니다.

아래의 예는 시스템 레지스트리의 응용프로그램 섹션에 대한 배치와 값 형태를 설명합니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\
        …
            RegistryPathWhereLoaderIsIdentified\
            Loader\Module:REG_SZ:DirPathFileName
            Name\DescriptiveName:REG_SZ:User Friendly App Name
            Commands\GlobalCommandName1:REG_SZ:LocalCommandName1
                GlobalCommandName2:REG_SZ:LocalCommandName2
                GlobalCommandName3:REG_SZ:LocalCommandName3
                GlobalCommandName4:REG_SZ:LocalCommandName4
                GlobalCommandName5:REG_SZ:LocalCommandName5
            Groups\
                GroupName:REG_SZ:GroupName
            …

Module 값은 존재하여야 하지만 레지스트리안에 존재하고 사용되지는 않습니다. 이와 유사하게, User Friendly App Name 값은 주어져야 하지만 현재 사용되지는 않습니다.

Groups 키 내의 값은 명령과 마찬가지로 ObjectARX 응용프로그램의 명령 그룹을 유일하게 식별하기 위하여 사용될 수 있습니다.

시스템 레지스트리 정보 삭제하기


응용프로그램이 업그레이드되거나 제거될 경우 시스템 레지스트리에서 ObjectARX 응용프로그램 정보를 삭제하는 것이 유용할 수도 있습니다. ObjectARX API는 acrxRegisterApp() 함수에 대응되는 acrxUnregisterApp() 함수를 제공합니다. 이 함수는 시스템 레지스트리의 AutoCAD 섹션에서 응용프로그램의 정보를 제거합니다.


 


DEMANDLOAD 시스템 변수

AutoCAD DEMANDLOAD 시스템 변수는 ObjectARX 응용프로그램의 올리기 요구 선택사항을 제어합니다.

DEMANDLOAD 시스템 변수의 초기값은 응용프로그램에 대한 시스템 레지스트리에 실행 탐지 또는 프록시 객체 탐지의 두 가지 옵션이 지정될 때 AutoCAD가 설치될 때 응용프로그램의 올리기 요구할 수 있도록 설정됩니다. DEMANDLOAD의 설정은 AutoCAD 시작시의 올리기 요구 또는 시스템 레지스트리에 지정된 옵션들로 사용자나 응용프로그램이 요청한 올리기 요구에는 영향을 미치지 않습니다.

시스템 변수의 값으로는 아래와 같은 값들이 사용되며 조합해서 사용할 수도 있습니다.

  0
        모든 ObjectARX 응용프로그램의 올리기 요구를 불가능하게 합니다.

  1
        프록시 객체가 탐지되면 ObjectARX 응용프로그램의 올리기 요구를 가능하         게 합니다.

  2
        명령 실행이 탐지되면 ObjectARX 응용프로그램의 올리기 요구를 가능하게         합니다.

  3
        프록시 객체와 명령 실행이 탐지되면 ObjectARX 응용프로그램의 올리기 요         구를가능하게 합니다(초기값).

DEMANDLOAD 시스템 변수는 프록시 객체와 명령 실행이 탐지되면 올리기 요구가 가능하게 지정된 시스템 레지스트리 설정을 가진 모든 ObjectARX 응용프로그램의 올리기 요구 기능을 사용자에게 불가능하게 하도록 허용합니다.

사용자 객체 발견시 올리기 요구하기

사용자 객체가 들어있는 DWG 또는 DXF 파일이 로드되면 AutoCAD는 조합된 응용프로그램이 이미 로드되어 있는지 아닌지를 판단합니다. 조합된 응용프로그램이 로드되어 있지 않은 상태에서 DEMANDLOAD 시스템 변수의 첫 번째 비트가 설정된 경우에 AutoCAD는 응용프로그램과 이것의 올리기 모듈에 대한 정보를 윈도우즈 시스템 레지스트리에서 검색합니다. AutoCAD가 시스템 레지스트리에서 적당한 정보를 찾으면 응용프로그램을 로드합니다.

참 고 : 사용자 클래스의 발견에 따른 올리기 요구는 AcDbObject에서 파생된 클              래스와 함께 동작하는 경우에만 직접 또는 간접적으로 실행됩니다.

AutoCAD가 ObjectARX 응용프로그램 polysamp에 의해 만들어진 파일을 읽는다고 가정하여 예를 들면,

1  AutoCAD가 도면 파일을 읽어 나가면서 polysamp에 의해 만들어진 사용자     객체를 만나게 되면 polysamp 응용프로그램이 로드되었는지의 여부를 판단     합니다.

2  AutoCAD는 프록시 객체를 발견하면 응용프로그램의 올리기 요구를 하도록 설     정된 DEMANDLOAD 시스템 변수를 찾고, 시스템 레지스트리의 AutoCAD 응용     프로그램 섹션에서 polysamp 키이(key)를 검색합니다. AutoCAD는 이 키이에     서 응용프로그램이 로드될 수 있는지의 여부를 정의하는 LoadCtrls 값을 찾고,     polysamp 모듈의 전체 경로를 가지고 있는 RegPath 값을 찾습니다. 레지스     트리의 이 섹션은 아래와 같이 보일 것입니다.

    \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\R15.0\
        ACAD-1:409\
            Applications\PolyCAD\
                LoadCtrls:REG_DWORD:0xd
                RegPath:REG_SZ:
                    \\HKEY_LOCAL_MACHINE\SOFTWARE\PolySampInc
                            \polysamp

3  AutoCAD는 로드할 모듈의 디렉토리, 경로 및 파일명을 결정하기 위하여
    polysamp\Loader 키이를 읽습니다. 레지스트리의 이 섹션은 아래와 같이 보     일 것입니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\
            PolySampInc\polysamp\
                Loader\MODULE:REG_SZ:c:\polysampinc\arx\polyui.arx
                Name\PolySamp:REG_SZ:PolyCad

4  이 시점에서 AutoCAD는 ObjectARX 모듈을 로드하려고 시도합니다. 모듈이 성     공적으로 로드되면 AutoCAD는 kLoadDwgMsg 메시지를 보내기 위하여 응용     프로그램 핸들들의 목록에 방금 로드된 응용프로그램의 핸들을 추가합니다. 이     후 AutoCAD는 응용프로그램이 올바르게 로드되었는지를 검사하고, 등록된 사     용자 클래스인지를 검사합니다. 응용프로그램이 성공적으로 로드되면
    AutoCAD는 당연히 도면 파일의 올리기를 계속합니다. ObjectARX 모듈이 로드     될 수 없거나 클래스를 사용할 수 없는 경우에 사용자 객체는 프록시로 간주되     고 도면 파일의 올리기가 계속됩니다.

명령 실행시 올리기 요구하기

AutoCAD는 사용자가 AutoCAD에 등록되지 않은 명령을 실행하면 이에 적당한 ObjectARX 응용프로그램을 올리려고 시도합니다.

ObjectARX 응용프로그램의 설치 프로그램은 명령 실행시의 올리기 요구를 지원하기 위해서 응용프로그램의 명령에 대한 시스템 레지스트리에 적절한 키이들과 값들을 만들어야만 합니다. 시스템 레지스트리의 응용프로그램 명령 섹션은 아래와 같은 정보들을 가지고 있을 것입니다.

        \\HKEY_LOCAL_MACHINE\SOFTWARE\
            Autodesk\ …
        …
            PolySampInc\polysamp\
                    Loader\MODULE:REG_SZ:c:\polysampinc\arx\polyui.arx
                    Name\PolySamp:REG_SZ:PolyCad
                    Commands\
                        ASDKPOLY:REG_SZ:ASDKPOLY
                        ASDKDRAGPOLY:REG_SZ:ASDKDRAGPOLY
                        ASDKPOLYEDIT:REG_SZ:ASDKPOLYEDIT
                    Groups\
                        ASDK:REG_SZ:ASDK
        …

이 예에서 개발자의 등록된 개발자 접두어 ASDK가 다른 응용프로그램 명령과의 충돌을 피하기 위하여 모든 명령의 접두어로 사용됩니다.

또한 ObjectARX 응용프로그램은 명령 실행시 올리기 요구를 처리하기 위한 적절한 acedRegCmds 매크로의 호출을 가지고 있어야만 합니다.

AutoCAD 시작시 올리기 요구하기

AutoCAD를 시작할 때의 ObjectARX 응용프로그램의 올리기 요구는 아래와 같이 시스템 레지스트리의 LoadCtrls 값을 0x02로 설정하여 지정될 수 있습니다.

    \\HKEY_LOCAL_MACHINE\SOFTWARE\Autodesk\AutoCAD\R15.0\
        ACAD-1:409\
            Applications\PolyCAD\
                LoadCtrls:REG_DWORD:0x02
                RegPath:REG_SZ:

시스템 레지스트리를 사용하여 응용프로그램 조작하기

올리기 요구에 관한 시스템 레지스트리 정보가 만들어지면 같은 정보가 올리기 요구 기능과는 별개로 ObjectARX 함수들의 올리기, 내리기 및 현재 메모리에 존재하는지의 여부를 검사하기 위하여 사용될 수 있습니다. ObjectARX 함수들의 처음 두 개의 인수로 사용되는 AppName 인수는 논리적인 응용프로그램 이름입니다.

아래의 ObjectARX 함수는 등록된 응용프로그램 이름을 사용합니다.

        bool acrxLoadApp (“AppName”)

이 함수는 메모리에 올리고자 하는 응용프로그램의 논리적인 이름을 대소문자를 구별하여 표현하는 한 개의 인수를 필요로 합니다. 이 함수는 올리기가 성공하면 1을 리턴하고, 실패하면 0을 리턴합니다.

        bool acrxUnloadApp (“AppName”)

위의 함수는 이미 올려진 응용프로그램의 논리적인 이름을 대소문자를 구별하여 표현하는 한 개의 인수를 필요로 합니다. 이 함수는 올리기가 성공하면 1을 리턴하고, 실패하면 0을 리턴합니다.

        void *acrxLoadedApps ()

이 함수는 현재 올려져 있는 각 응용프로그램의 논리적인 응용프로그램 이름을 void *로서 문자열들의 배열을 리턴합니다.이 함수는 올려진 응용프로그램이 없는 경우에는 NULL을 리턴합니다.


 












ObjectARX 명령
 
 

ARX 명령과 선택사항에 대해 설명합니다. 초기 프롬프트는 다음과 같습니다.

        ?/Load/Unload/Commands/Options: 선택사항을 입력하거나 ENTER를 누릅니다.

  ? (응용프로그램 리스트)
        현재 올려진 응용프로그램 목록을 나열합니다.

  Load
        표준 파일 대화상자에서 지정한 .arx  파일을 올립니다. 만일 FILEDIA 시스템 변수가 0으로 설정되         었다면 대화상자가 디스플레이되지 않고 아래와 같은 프롬프트가 표시될 때 올리고자 하는 파일의         이름을 입력해야 합니다.

            Runtime extension file: 파일명을 입력합니다.

  Unload
        지정된 ARX 프로그램을 내립니다. 일부 응용프로그램들은 내려질 수 없습니다.

  Commands
        ARX 프로그램에 등록된 명령 그룹내의 모든 명령 이름을 디스플레이합니다.

  Options
        개발자와 관련된 ARX 응용프로그램 선택사항을 표시합니다.

            Options (Group/CLasses/Services): 선택사항을 입력합니다.

            Group
                AutoCAD가 명령 이름을 식별할 때 ARX 응용프로그램에서 등록된 명령중 지정된 명령 그룹                 이 첫 번째로 검색되는 그룹이 되도록 합니다. 다른 등록된 그룹이 있으면 이전에 ARX 명령이                 실행되었던 것과 같은 순서로 검색됩니다.

                    Command Group Name: 명령 그룹 이름을 입력합니다.

                검색 순서는 명령 이름이 다중 그룹으로 구성되어 있는 경우에만 중요합니다. 이 메커니즘은                 서로 다른 ARX 응용프로그램들이 분리된 자신의 명령 그룹내에서 같은 명령 이름으로 정의                 하는 것을 허용합니다. 명령 그룹을 정의한 ARX 응용프로그램은 자체 사용 설명서에 그룹 이                 름을 발표해야 합니다.

                그룹은 사용자가 직접 선택하도록 의도되지는 않았습니다. 사용자는 그룹 옵션으로 ARX 명                 령을 실행하는 스크립트와 조합하여 첫 번째로 검색될 그룹을 지정합니다. 이 기능은 보통 키                 메뉴 항목 스크립트에 삽입됩니다. 사용자는 스크립트로부터 메뉴 항목을 선택합니다. 키 메                 뉴 항목 스크립트는 다른 응용프로그램의 명령에 우선하는 선행 응용프로그램으로부터 기능                 적으로는 다를지라도 같은 이름의 명령이 주어질 때 첫 번째로 검색될 그룹을 규정하는 그룹                 옵션을 실행합니다.

                예를 들어, ABC라는 건축용 응용프로그램과 XYZ라는 인테리어용 응용프로그램은 각각 ABC                 와 XYZ 명령 그룹을 정의했다고 가정합시다. ABC 건축용 프로그램의 대부분의 명령은 건축                 전문 용어로서 정의하고, XYZ 인테리어 프로그램의 대부분의 명령은 수식이 많은 인테리어                 전문 용어로 정의하였지만 두 응용프로그램 모두에 INVENTORYORDERS라는 명령이                 동시에 정의되었다고 합시다. 사용자는 ABC 건축용 응용프로그램에 의해 정의된 메뉴 항목                 을 선택하고 다음 스크립트를 실행합니다.

                    ARX
                    Group
                    ABC

                스크립트는 우선 순위를 맨 위에 놓고 ABC 건축용 버전의 명령으로 INVENTORY 명령을 실                 행하기 위해 ABC 건축용 명령 세트를 맨 위에 놓습니다. 이후 인테리어 디자이너가 같은 세                 트로 올려진 응용프로그램상에서 도면 작업을 할 때, 키 아이콘 선택은 XYZ 인테리어 명령이                 선행되도록 합니다.

                참 고 : 명령 그룹은 AutoLISP에서 정의된 명령 또는 ObjectARX 응용프로그램에서
                           acedDefun() 함수를 호출하여 정의된 명령과는 관련이 없습니다.

            Classes
                AutoCAD 또는 ARX 프로그램에 의해 등록되었는지의 여부에 관계없이 시스템에 등록된 객체                 로부터 파생된 C++ 클래스의 클래스 계층구조를 보여줍니다..

            Services
                AutoCAD 또는 ARX 프로그램에 의해 등록된 모든 서비스 이름의 목록을 나열합니다.


 












AutoLISP에서 ObjectARX 응용프로그램 실행하기
 
 

ObjectARX 응용프로그램은 acedDefun() 함수를 사용하여 외부 함수로서 AutoLISP에서 사용할 수 있는 함수들을 정의할 수 있습니다. 응용프로그램이 올려진 후에는 명령을 실행하거나 사용자가 정의한 AutoLISP 함수로 정확하게 외부 함수를 실행할 수 있습니다. AutoLISP 변수는 외부 함수의 인수로 전달될 수 있으며, 외부 함수는 그 결과를 리턴할 수 있습니다.또한 외부 함수는 키보드, 점의 지정 및 좌표 입력장치로 객체에 대한 입력을 사용자에게 제공할 수 있고, Windows나 AutoCAD 관련 도움말을 설정할 수 있습니다.

외부 함수는 AutoLISP 함수와 상호동작적으로 실행될 수 있습니다. ObjectARX 응용프로그램은 AutoLISP 함수를 호출할 수 없습니다. 그렇지만 ObjectARX 응용프로그램은 AutoLISP의 기호값을 가져오거나 설정할 수 있습니다.

ObjectARX 응용프로그램은 AutoLISP과 같이 C:XXX 형태의 새로운 AutoCAD 명령을 정의할 수 있습니다. 이렇게 정의된 함수는 명령행 프롬프트에서 괄호없이 이름을 입력하여 실행할 수 있습니다.

외부 함수의 정의는 이전의 같은 이름을 가진 정의를 대치시킵니다. 두 개의 ObjectARX 응용프로그램이 같은 이름으로 함수를 정의하였다면 첫 번째로 올려진 응용프로그램의 함수는 잃게 됩니다. 두 번째로 올려진 응용프로그램을 내리더라도 중복된 함수를 호출할 수는 없습니다.


 












오류 처리하기
 
 

아래의 예제는 이제까지 살펴보았던 여러 예들에 대한 오류 검사의 적절한 사용법을 보여줍니다.

        Acad::ErrorStatus
        createCircle(AcDbObjectId& circleId)
        {
            circleId = AcDbObjectId::kNull;
            AcGePoint3d center(9.0, 3.0, 0.0);
            AcGeVector3d normal(0.0, 0.0, 1.0);
            AcDbCircle *pCirc = new AcDbCircle(center, normal, 2.0);
            if (pCirc == NULL)
                return Acad::eOutOfMemory;
            AcDbBlockTable *pBlockTable;
            Acad::ErrorStatus es = acdbHostApplicationServices()->workingDatabase()->
                    getSymbolTable(pBlockTable, AcDb::kForRead);
            if (es != Acad::eOk) {
                delete pCirc;
                return es;
            }
            AcDbBlockTableRecord *pBlockTableRecord;
            es = pBlockTable->getAt(ACDB_MODEL_SPACE, pBlockTableRecord, AcDb::kForWrite);
            if (es != Acad::eOk) {
                Acad::ErrorStatus es2 = pBlockTable->close();
                if (es2 != Acad::eOk) {
                    acrx_abort(“\nApp X failed to close Block”
                        ” Table. Error: %d”, acadErrorStatusText(es2));
                }
                delete pCirc;
                return es;
            }
            es = pBlockTable->close();
            if (es != Acad::eOk) {
                acrx_abort(“\nApp X failed to close Block Table.”
                    ” Error: %d”, acadErrorStatusText(es));
            }
            es = pBlockTableRecord->appendAcDbEntity(circleId, pCirc);
            if (es != Acad::eOk) {
                Acad::ErrorStatus es2 = pBlockTableRecord->close();
                if (es2 != Acad::eOk) {
                    acrx_abort(“\nApp X failed to close”
                        ” Model Space Block Record. Error: %s”,
                        acadErrorStatusText(es2));
                }
                delete pCirc;
                return es;
            }
            es = pBlockTableRecord->close();
            if (es != Acad::eOk) {
                acrx_abort(“\nApp X failed to close”
                    ” Model Space Block Record. Error: %d”,
                    acadErrorStatusText(es));
            }
            es = pCirc->close();
            if (es != Acad::eOk) {
                acrx_abort(“\nApp X failed to” ” close circle entity. Error: %d”,
                    acadErrorStatusText(es));
            }
            return es;
        }

        Acad::ErrorStatus
        createNewLayer()
        {
            AcDbLayerTableRecord *pLayerTableRecord
                = new AcDbLayerTableRecord;
            if (pLayerTableRecord == NULL)
                return Acad::eOutOfMemory;
            Acad::ErrorStatus es = pLayerTableRecord->setName(“ASDK_MYLAYER”);
            if (es != Acad::eOk) {
                delete pLayerTableRecord;
                return es;
            }
            AcDbLayerTable *pLayerTable;
            es = acdbHostApplicationServices()->workingDatabase()->
                getSymbolTable(pLayerTable, AcDb::kForWrite);
            if (es != Acad::eOk) {
                delete pLayerTableRecord;
                return es;
            }
            // The linetype object ID default is 0, which is
            // not a valid ID. Therefore, it must be set to a
            // valid ID, the CONTINUOUS linetype.
            // Other data members have valid defaults, so
            // they can be left alone.
            //
            AcDbLinetypeTable *pLinetypeTbl;
            es = acdbHostApplicationServices()->workingDatabase()->
                getSymbolTable(pLinetypeTbl, AcDb::kForRead);
            if (es != Acad::eOk) {
                delete pLayerTableRecord;
                es = pLayerTable->close();
                if (es != Acad::eOk) {
                    acrx_abort(“\nApp X failed to close Layer”
                        ” Table. Error: %d”, acadErrorStatusText(es));
                }
                return es;
            }
            AcDbObjectId ltypeObjId;
            es = pLinetypeTbl->getAt(“CONTINUOUS”, ltypeObjId);
            if (es != Acad::eOk) {
                delete pLayerTableRecord;
                es = pLayerTable->close();
                if (es != Acad::eOk) {
                    acrx_abort(“\nApp X failed to close Layer”
                        ” Table. Error: %d”, acadErrorStatusText(es));
                }
                return es;
            }
            pLayerTableRecord->setLinetypeObjectId(ltypeObjId);
            es = pLayerTable->add(pLayerTableRecord);
            if (es != Acad::eOk) {
                Acad::ErrorStatus es2 = pLayerTable->close();
                if (es2 != Acad::eOk) {
                    acrx_abort(“\nApp X failed to close Layer”
                        ” Table. Error: %d”, acadErrorStatusText(es2));
                }
                delete pLayerTableRecord;
                return es;
            }
            es = pLayerTable->close();
            if (es != Acad::eOk) {
                acrx_abort(“\nApp X failed to close Layer”
                    ” Table. Error: %d”, acadErrorStatusText(es));
            }
            es = pLayerTableRecord->close();
            if (es != Acad::eOk) {
                acrx_abort(“\nApp X failed to close Layer”
                    ” Table Record. Error: %d”, acadErrorStatusText(es));
            }
            return es;
        }



답글 남기기

이메일 주소는 공개되지 않습니다.