.dwg文件的读取。拥有RealDWG或者ObjectARX不必多说。
安装RealDWG后RealDWG目录下的Samples看看。
新建工程配置好Inc,Lib,附加依赖等。
不必多说。
需要将AcDbHostApplicationServices实现一遍。
sample自带的即可,也可自己按照自己的来写。
1 int Verbose = 0; 2 int Copy = 0; 3 int Header = 0; 4 int Tables = 0; 5 int doExtents = 0; 6 int showErased = 0; 7 int resolveXrefs = 0; 8 9 class DumpDwgHostApp : public AcDbHostApplicationServices 10 { 11 public: 12 ~DumpDwgHostApp(); 13 Acad::ErrorStatus findFile(TCHAR* pcFullPathOut, int nBufferLength, 14 const TCHAR* pcFilename, AcDbDatabase* pDb = NULL, 15 AcDbHostApplicationServices::FindFileHint = kDefault); 16 // These two functions return the full path to the root folder where roamable/local 17 // customizable files were installed. Note that the user may have reconfigured 18 // the location of some the customizable files using the Options Dialog 19 // therefore these functions should not be used to locate customizable files. 20 // To locate customizable files either use the findFile function or the 21 // appropriate system variable for the given file type. 22 // 23 Acad::ErrorStatus getRoamableRootFolder(const TCHAR*& folder); 24 Acad::ErrorStatus getLocalRootFolder(const TCHAR*& folder); 25 26 //URL related services 27 Adesk::Boolean isURL(const TCHAR* pszURL) const; 28 Adesk::Boolean isRemoteFile(const TCHAR* pszLocalFile, TCHAR* pszURL, size_t nUrlSize) const; 29 Acad::ErrorStatus getRemoteFile(const TCHAR* pszURL, TCHAR* pszLocalFile, size_t nFilePath, Adesk::Boolean bIgnoreCache) const; 30 31 // make sure you implement getAlternateFontName. In case your findFile implementation 32 // fails to find a font you should return a font name here that is guaranteed to exist. 33 virtual TCHAR * getAlternateFontName() const 34 { 35 return _T("txt.shx"); //findFile will be called again with this name 36 } 37 private: 38 mutable CMapStringToString m_localToUrl; 39 }; 40 DumpDwgHostApp::~DumpDwgHostApp() 41 { 42 CString local,url; 43 for (POSITION pos = m_localToUrl.GetStartPosition();pos!=NULL;) 44 { 45 m_localToUrl.GetNextAssoc(pos,local,url); 46 DeleteUrlCacheEntry(url); 47 } 48 } 49 // Return the Install directory for customizable files 50 Acad::ErrorStatus 51 DumpDwgHostApp::getRoamableRootFolder(const TCHAR*& folder) 52 { 53 Acad::ErrorStatus ret = Acad::eOk; 54 static TCHAR buf[MAX_PATH] = _T("\0"); //MDI SAFE 55 if (buf[0]==0) 56 if (GetModuleFileName(NULL, buf, MAX_PATH) != 0) 57 ret = Acad::eRegistryAccessError; 58 folder = buf; 59 return ret; 60 } 61 62 // Return the Install directory for customizable files 63 Acad::ErrorStatus 64 DumpDwgHostApp::getLocalRootFolder(const TCHAR*& folder) 65 { 66 Acad::ErrorStatus ret = Acad::eOk; 67 static TCHAR buf[MAX_PATH] = _T("\0"); //MDI SAFE 68 if (buf[0]==0) 69 if (GetModuleFileName(NULL, buf, MAX_PATH) != 0) 70 ret = Acad::eRegistryAccessError; 71 folder = buf; 72 return ret; 73 } 74 75 Acad::ErrorStatus 76 DumpDwgHostApp::findFile(TCHAR* pcFullPathOut, int nBufferLength, 77 const TCHAR* pcFilename, AcDbDatabase* pDb, 78 AcDbHostApplicationServices::FindFileHint hint) 79 { 80 TCHAR pExtension[5]; 81 switch (hint) 82 { 83 case kCompiledShapeFile: 84 _tcscpy(pExtension, _T(".shx")); 85 break; 86 case kTrueTypeFontFile: 87 _tcscpy(pExtension, _T(".ttf")); 88 break; 89 case kPatternFile: 90 _tcscpy(pExtension, _T(".pat")); 91 break; 92 case kARXApplication: 93 _tcscpy(pExtension, _T(".dbx")); 94 break; 95 case kFontMapFile: 96 _tcscpy(pExtension, _T(".fmp")); 97 break; 98 case kXRefDrawing: 99 _tcscpy(pExtension, _T(".dwg"));100 break;101 case kFontFile: // Fall through. These could have102 case kEmbeddedImageFile: // various extensions103 default:104 pExtension[0] = _T('\0');105 break;106 }107 TCHAR* filePart;108 DWORD result;109 result = SearchPath(NULL, pcFilename, pExtension, nBufferLength, 110 pcFullPathOut, &filePart);111 if (result && result < (DWORD)nBufferLength)112 return Acad::eOk;113 else114 return Acad::eFileNotFound;115 }116 Adesk::Boolean 117 DumpDwgHostApp::isURL(const TCHAR* pszURL) const118 {119 return PathIsURL(pszURL);120 }121 122 Adesk::Boolean 123 DumpDwgHostApp::isRemoteFile(const TCHAR* pszLocalFile, TCHAR* pszURL, size_t nUrlSize) const124 {125 CString value;126 if (m_localToUrl.Lookup(pszLocalFile,value))127 {128 _tcscpy_s(pszURL, nUrlSize, value);129 return TRUE;130 }131 return FALSE;132 }133 134 Acad::ErrorStatus 135 DumpDwgHostApp::getRemoteFile(const TCHAR* pszURL, TCHAR* pszLocalFile, size_t nFilePath, Adesk::Boolean bIgnoreCache) const136 {137 DWORD err = ERROR_FILE_NOT_FOUND;138 if (!bIgnoreCache)139 {140 DWORD size = 0;141 if (GetUrlCacheEntryInfo(pszURL,NULL,&size))142 return Acad::eInetFileGenericError; //this shouldn't succeed143 err = GetLastError();144 if (err == ERROR_INSUFFICIENT_BUFFER)145 {146 INTERNET_CACHE_ENTRY_INFO* pCacheEntry = (INTERNET_CACHE_ENTRY_INFO*)malloc(size);147 if (GetUrlCacheEntryInfo(pszURL,pCacheEntry,&size))148 {149 _tcscpy_s(pszLocalFile, nFilePath, pCacheEntry->lpszLocalFileName);150 m_localToUrl.SetAt(pszLocalFile,pszURL);151 free(pCacheEntry);152 return Acad::eInetOk;153 }154 err = GetLastError();155 }156 }157 if (err == ERROR_FILE_NOT_FOUND)158 {159 if (SUCCEEDED(URLDownloadToCacheFile(NULL,pszURL,pszLocalFile,_MAX_PATH,0,NULL)))160 {161 m_localToUrl.SetAt(pszLocalFile,pszURL);162 return Acad::eInetOk;163 }164 }165 return Acad::eInetFileGenericError;166 }
到此进入正题:
1 void createScene() 2 { 3 acdbSetHostApplicationServices(&gDumpDwgHostApp); 4 long lcid = 0x00000409; // English 5 acdbValidateSetup(lcid); 6 7 acrxLoadModule(acIsmObjDbxFile, 0); 8 9 Ogre::Entity* ent = mSceneMgr->createEntity("myentity", "person.mesh"); 10 //ent-> 11 12 Ogre::SceneNode* node1 = mSceneMgr->createSceneNode("node1"); 13 node1->setPosition(1177, 702, 0); 14 mSceneMgr->getRootSceneNode()->addChild(node1); 15 node1->attachObject(ent); 16 node1->setScale(0.1,0.1,0.1); 17 18 Ogre::Entity* ent2 = mSceneMgr->createEntity("myentity2", "Sinbad.mesh"); 19 Ogre::SceneNode* node2 = mSceneMgr->createSceneNode("node2"); 20 node2->setPosition(1410, 900, 10); 21 node1->addChild(node2); 22 node2->attachObject(ent2); 23 24 25 ManualObject* manual = mSceneMgr->createManualObject("manual"); 26 manual->begin("BaseWhiteNoLighting", RenderOperation::OT_LINE_LIST); 27 28 29 AcDbDatabase *pDb = new AcDbDatabase(Adesk::kFalse); 30 if (pDb == NULL) 31 return; 32 33 //_tprintf(_T("%s\n"), L"E:\\yu\\Drawi11ng1.dwg"); 34 35 TCHAR drive[_MAX_DRIVE] = _T(""); 36 TCHAR dir[_MAX_DIR] = _T(""); 37 TCHAR fname[_MAX_FNAME] = _T(""); 38 TCHAR ext[_MAX_EXT] = _T(""); 39 40 _tsplitpath_s(L"E:\\yu\\Drawi11ng1.dwg", drive, dir, fname, ext); 41 42 if (_tcsicmp(ext, _T(".dwg")) && _tcscmp(ext, _T(".dxf"))) 43 { 44 _tprintf(_T("Can't open %s\n"), L"E:\\yu\\Drawi11ng1.dwg"); 45 _tprintf(_T("File must have .dwg or .dxf extension\n")); 46 delete pDb; 47 return; 48 } 49 50 if(pDb->readDwgFile(L"E:\\yu\\Drawi11ng1.dwg") == Acad::eOk) 51 { 52 acdbHostApplicationServices()->setWorkingDatabase(pDb); 53 int ntet = 1; 54 } 55 56 AcDbLayerTable* pLayerTbl; 57 pDb->getSymbolTable(pLayerTbl,AcDb::kForRead); 58 59 if(!pLayerTbl->has(L"568中段")) 60 { 61 _tprintf(_T("Don't have 568中段 \n")); 62 pLayerTbl->close(); 63 return; 64 } 65 66 AcDbObjectId layerId; //568中段 图层id 67 pLayerTbl->getAt(L"568中段",layerId); 68 pLayerTbl->close(); 69 70 //get blocktbl 71 AcDbBlockTable* pBlockTbl; 72 pDb->getSymbolTable(pBlockTbl,AcDb::kForRead); 73 74 AcDbBlockTableRecord *pBlockTableRecord; 75 pBlockTbl->getAt(ACDB_MODEL_SPACE, pBlockTableRecord, AcDb::kForRead); 76 pBlockTbl->close(); 77 78 //create AcDbBlockTableIterator 79 AcDbBlockTableRecordIterator* thlIter; 80 pBlockTableRecord->newIterator(thlIter); 81 AcDbEntity* pEnt; // 82 for(thlIter->start();!thlIter->done();thlIter->step()) 83 { 84 //利用遍历器获得每一个实体 85 thlIter->getEntity(pEnt,AcDb::kForWrite); 86 if(pEnt->layerId() == layerId) 87 { 88 //is line 89 AcDbLine* pLine = AcDbLine::cast(pEnt); 90 if(pLine != NULL) 91 { 92 //pLine 93 AcGePoint3d startP(0,0,0),endP(0,0,0); 94 startP = pLine->startPoint(); 95 endP = pLine->endPoint(); 96 printf("yu %s startX %lf,startY %lf,startZ %lf\n endX %lf,endY %lf,endZ %lf\n",(pEnt->isA())->name(),startP.x,startP.y,startP.z,endP.x,endP.y,endP.z); 97 manual->position(startP.x, startP.y, startP.z); // start position 98 manual->position( endP.x,endP.y, endP.z); // draw first line 99 }100 }101 102 pEnt->close();103 }104 delete thlIter;105 pBlockTableRecord->close();106 107 manual->end();108 109 mSceneMgr->getRootSceneNode()->createChildSceneNode()->attachObject(manual);110 111 // mSceneMgr->getRootSceneNode()->attachObject(ent);112 }113 114 private:115 116 };
这里有些无关紧要的代码,大家不要介意。看重点即可,新建一个数据库对象 AcDbDatabase *pDb = new AcDbDatabase(Adesk::kFalse);
打开一个DWG文件 pDb->readDwgFile(L"E:\\yu\\Drawi11ng1.dwg") == Acad::eOk,当然可以打开指定的文件,也有打开多个DWG的,这里就不细说;打开模型空间块表记录,遍历模型空间块表记录,找到符合自己要求的数据,读取即可。
cad图:
读取后显示效果图:
到此,打开dwg文件,读取指定数据,用OGRE显示均正常,结束。
插入cj小美女镇楼: