Hello
We are a company that uses MICROSTATION software to deploy our own solution “Dkmètre” that we have developed with the C and MDL languages.
One of the functionalities that Dkmètre offers is “placing terrain points”.
The user selects this feature from a range of Dkmètre added at MICROSTATION, then, he places a point in the DGN. Later, a command box is automatically opened asking the user to enter the altitude of the point.
This feature works often properly, but when we change the current DGN file without closing Dkmètre (so, not reset variables used in Dkmètre) and we chose this feature in the new DGN file it does not work and it causes a bug.
Debugging Dkmètre code shows that the bug is launched after executing the mdl function “mdlState_startPrimitive( DkmComposite_FirstPoint, DkmComposite_StartCommand, MesDKM_Place_Courbe_Composite, MesDKM_Entree_le_premier_point_de_la_courbe );”
I note that the DkmComposite_FirstPoint function is the function called when the user chooses to place a new terrain point.
You find bellow the code source of the functions DkmComposite_FirstPoint and DkmComposite_StartCommand and the values of the constants MesDKM_Place_Courbe_Composite and MesDKM_Entree_le_premier_point_de_la_courbe
#define MesDKM_Place_Courbe_Composite 1168
#define MesDKM_Entree_le_premier_point_de_la_courbe 654
DkmComposite_FirstPoint
void DkmComposite_FirstPoint( Dpoint3d * point, int view ){ int status = 0; /**/ST_ARTICLEMETRE articleMetre;/**/ paramEtudeP->recupererSymboDessin = FALSE; if( glbP->composite.orientationObjets != 2 ) if( DkmComposite_saisieZ( glbP->composite.orientationObjets == 0 ? point : &glbP->composite.dernierPt, status, view ) == ERROR ) return; if( glbP->composite.orientationObjets != 1 ) { DkmComposite_forcePlanaire( point, view, TRUE, FALSE ); glbP->composite.dernierPt.x = point->x; glbP->composite.dernierPt.y = point->y; glbP->composite.dernierPt.z = 0.0; glbP->composite.tg.x = glbP->composite.tg.y = 0.0; glbP->composite.tg.z = 0.0; }
glbP->composite.commandeStarted = TRUE; DkmComposite_enableOptions( NULL ); if( glbP->composite.objets ) { if( glbP->composite.orientationObjets == 2 ) glbP->composite.orientationObjets = 1; else DkmComposite_StartCommand( ); } else DkmComposite_StartSegment( );}
DkmComposite_StartCommand
void DkmComposite_StartCommand( void ){ mdlOutput_message( DkmMessage( MesDKM_Entree_Le_point_suivant_de_la_courbe ) );mdlState_startPrimitive( DkmComposite_FirstPoint, DkmComposite_StartCommand, MesDKM_Place_Courbe_Composite,
MesDKM_Entree_le_premier_point_de_la_courbe ); mdlState_setFunction( STATE_COMPLEX_DYNAMICS, DkmComposite_Curseur ); mdlState_setFunction( STATE_COMMAND_CLEANUP, DkmComposite_CleanUpFunction ); mdlState_setFunction( STATE_RESET, DkmComposite_resetRestartCommand ); mdlSystem_setFunction( SYSTEM_SYMBOLOGY_CHANGE, __DkmComposite_SymbologyChanged__ ); mdlSystem_setFunction( SYSTEM_LEVEL_CHANGE, __DkmComposite_SymbologyChanged__ ); glbP->composite.dgnModelRef = MASTERFILE; glbP->composite.commandeStarted = FALSE; glbP->composite.orientationObjets = 0; glbP->composite.angleObjet = 0.0; DkmComposite_enableOptions( NULL ); mdlAccuSnap_enableSnap( TRUE ); mdlAccuSnap_enableLocate( TRUE );}
the bug starts at the code written in red
You have installed a cleanup function for this, is this called properly ? I assume your application runs vis MS_DGNAPPS, have you installed a callback that informs you about the changing dgn file ?
i.e. mdlSystem_setFunction (SYSTEM_NEW_DESIGN_FILE, mdl_changeDGNFile);
with something like that
Public void mdl_changeDGNFile(char *filename, int state){ int i; // state SYSTEM_NEWFILE_CLOSE before old dgn is closed // state SYSTEM_NEWFILE_COMPLETE after new dgn is opened if (state == SYSTEM_NEWFILE_COMPLETE) { // tell the dialog(s) that the file has been changed dll_changeDGN(); // reset the value for global access gCurrentModel = NULL; } if (state == SYSTEM_NEWFILE_CLOSE) { dll_callFunction(DLL_UNLOADDGN, (void*) filename); }}
both the dll_... functions react here on the closing or finished loading of a new designfile. This is the place where you might reset your values. You even have to asure that your global elementDescrP is correctly freed when switching files. Otherwise you will produce memory leaks and/or unconditional behaviour (if mistakenly freed after the corresponding memory was freed. You even have to asure that your cleanup-function works correctly, it might still be installed if you haven't done something to avoid this, and might expect a situation that is (no longer) valid.
HTH Michael
Answer Verified By: cdiTech
I find in the source code a function similar to the mdl_changeDGNFile function but it does not contains all the necessary code in order to free all the variables. I added the some code and it works fine :)
thank you for your help.