3D PLM PPR Hub Open Gateway |
Product Modeler |
Inserting Components Stored in Foreign FilesImplementing the CATIProductFileSelection Interface |
Use Case |
AbstractThis article presents the CAAPstProductFileSelection use case which illustrates how to add products contained in a foreign file format. |
Using the CATIProductFileSelection interface, a component stored in a foreign file format can be loaded and inserted into an existing product.
[Top]
CAAPstProductFileSelection is a use case of the CAAProductStructure.edu framework that illustrates the ProductStructure framework capabilities.
[Top]
Components are inserted into a product by activating the Components -> Existing Component... contextual menu and selecting one or more files. By implementing the CATIProductFileSelection interface, we will show how to make that menu recognize new file types and how those files can be processed for insertion.
This implementation is designed specifically to
The sample CAAProduct file is in fact a CATProduct file that has been renamed. It has five child products and can be found at
InstallRoot/CAAProductStructure.edu/CNext/resources/graphic/CAAPstProductFileSelection_MainPrd.CAAProduct
[Top]
To launch CAAPstProductFileSelection:
# CAAPstProductFileSelection use case CAAPstPrdFileSel CATIProductFileSelection libCAAPstProductFileSelection |
[Top]
CAAPstProductFileSelection code is located in the CAAPstProductFileSelection.m module of the CAAProductStructure.edu framework.
[Top]
There are two parts in CAAPstProductFileSelection:
[Top]
The impact on the user interface is the appearance of the new CAAProduct file type with a corresponding label in the file selection dialog. This is done with the help of the dictionary and two resource files.
In the dictionary we indicate that our implementation CAAPstPrdFileSel, implements the CATIProductFileSelection interface with code residing in the libCAAPstProductFileSelection library:
# CAAPstProductFileSelection use case CAAPstPrdFileSel CATIProductFileSelection libCAAPstProductFileSelection |
As a consequence, there must be a CAAPstPrdFileSel.CATRsc file describing the file type that CAAPstPrdFileSel will handle. This file can found at
InstallRoot/CAAProductStructure.edu/CNext/resources/msgcatalog/CAAPstPrdFileSel.CATRsc
ExtensionCount="1"; 1.Method="CAA Product File"; 1.Extension="CAAProduct"; |
The CAAPstPrdFileSel.CATRsc file indicates that one type is handled (ExtensionCount="1") and that the extension is "CAAProduct". The Method line serves as a unique identification in case there are more than one implementation handling the CAAProduct file type.
Finally we need a localized label for the CAAProduct file type. It is defined by the CAAPstPrdFileSel.CATNls file that is located at
InstallRoot/CAAProductStructure.edu/CNext/resources/msgcatalog/CAAPstPrdFileSel.CATNls
1="CAA Product Files "; |
The contents of this file can be translated for other locales if needed. In that case, they should be located in the corresponding locale directory. For example, you can find the French version in
InstallRoot/CAAProductStructure.edu/CNext/resources/msgcatalog/French/CAAPstPrdFileSel.CATNls
Now that the user interface recognizes the new file type, the logic that processes the files must also be provided.
[Top]
The CATIProductFileSelection interface implementation has to be derived from the CATPrdCommonFileSelection class. It has two methods that can be redefined:
In our CAAPstProductFileSelection class, we need to redefine only ExtractProducts for the specific behavior (of extracting only the second child product) and the constructor/destructor to add the CAAProduct file type.
class CAAPstProductFileSelection: public CATPrdCommonFileSelection { CATDeclareClass; public: // Standard constructor and destructor for an implementation class // ----------------------------------------------------------------- CAAPstProductFileSelection (); virtual ~CAAPstProductFileSelection (); /** * @see ProductStructure.CATIProductFileSelection#ExtractProducts() */ HRESULT ExtractProducts (CATIContainer*, CATIProduct*, CATListValCATBaseUnknown_var*&); private: // The copy constructor and the = operator must not be implemented // ------------------------------------------------------------------- CAAPstProductFileSelection (CAAPstProductFileSelection &); CAAPstProductFileSelection& operator=(CAAPstProductFileSelection&); }; |
There are roughly three parts in the CAAPstProductFileSelection.cpp source file:
[Top]
The C++ class is linked to the interface with the TIEchain macro.The ClassImplementClass macro indicates that the C++ class is a data extension and that it is extending CAAPstPrdFileSel.
TIEchain_CATIProductFileSelection(CAAPstProductFileSelection); CATImplementClass(CAAPstProductFileSelection, DataExtension, CATBaseUnknown, CAAPstPrdFileSel); |
[Top]
In the constructor, the _typesList data member is allocated and initialized with a list consisting of "CAAProduct". This is how CATIA determines which implementation to invoke for a given file type. This data member is freed in the destructor if necessary.
//----------------------------------------------------------------------------- // Constructor //----------------------------------------------------------------------------- CAAPstProductFileSelection::CAAPstProductFileSelection(): CATPrdCommonFileSelection() { CAAPstPFSTRACE("CAAPstProductFileSelection - Constructor"); _typesList = new CATListOfCATUnicodeString(1); if (NULL != _typesList) { // must be identical to the one in CAApstPrdFileSel.CATRsc _typesList->Append("CAAProduct"); } } //----------------------------------------------------------------------------- // Destructor //----------------------------------------------------------------------------- CAAPstProductFileSelection::~CAAPstProductFileSelection() { CAAPstPFSTRACE("CAAPstProductFileSelection - Destructor"); if (NULL != _typesList) { delete _typesList; _typesList = NULL; } } |
[Top]
Once the user has selected one or more files, this method is invoked. The purpose of this method is to process the selected files and return a list of components from it.
ExtractProducts is called with three input parameters (one data member and two arguments) and one output parameter:
//----------------------------------------------------------------------------- // ExtractProducts //----------------------------------------------------------------------------- HRESULT CAAPstProductFileSelection::ExtractProducts (CATIContainer* iContainer, // container of parent product CATIProduct* iParentProduct, // parent product to insert to CATListValCATBaseUnknown_var*& oList) // products to be inserted { HRESULT rc; CAAPstPFSTRACE("Entering CAAPstProductFileSelection::ExtractProducts"); |
The inputs are verified and the output list is allocated.
... if (NULL == _pathsList || NULL == iContainer || NULL == iParentProduct) return E_FAIL; int pathCount = _pathsList->Size(); if (NULL == oList) { // allocate product list oList = new CATLISTV(CATBaseUnknown_var) (pathCount); if (NULL == oList) { CAAPstPFSTRACE("Failed to allocate output list"); return E_FAIL; } } ... |
Then for each file, we extract the second child product and add it to the output list.
... for (int pathNum = 1; pathNum <= pathCount; pathNum++) { // // For each file selected, // retrieve the 2nd child product for insertion // CATUnicodeString& curPath = (*_pathsList)[pathNum]; CATDocument* pSelectedDoc = NULL; rc = CATDocumentServices::Open(curPath, pSelectedDoc); ... CATIDocRoots* pDocRoots = NULL; rc = pSelectedDoc->QueryInterface(IID_CATIDocRoots, (void **) &pDocRoots); ... CATListValCATBaseUnknown_var* pRootProducts = pDocRoots->GiveDocRoots(); ... CATIProduct_var spRootProduct = (*pRootProducts)[1]; delete pRootProducts; pRootProducts = NULL; ... CATIProduct *pProductOnRoot = NULL; rc = spRootProduct->QueryInterface(IID_CATIProduct, (void **) &pProductOnRoot); ... CATListValCATBaseUnknown_var* childrenList = pProductOnRoot->GetAllChildren(); if (NULL == childrenList || childrenList->Size() < 2) { CAAPstPFSTRACE("Failed to get 2nd children of root product"); return E_FAIL; } CATIProduct_var spProductToAdd = (*childrenList)[selectedChild]; oList->Append(spProductToAdd); ... } CAAPstPFSTRACE("Exiting CAAPstProductFileSelection::ExtractProducts"); return S_OK; } |
[Top]
This use case has demonstrated how to handle a new file type:
[Top]
[1] | The Product Structure Model |
[2] | Building and Launching a CAA V5 Use Case |
[Top] |
Version: 1 [Aug 2004] | Document revised |
Version: 1 [Sep 2003] | Document created |
[Top] |
Copyright © 2003, Dassault Systèmes. All rights reserved.