User supplied callback procedure for converting modules into previous format.

    typedef GSErrCode  APIModulDataSaveOldFormatHandlerProc (
        API_FTypeID                                     planFileType,
        GS::HashTable<GS::UniString, API_ModulData*>&   modulesToSave



[in] The old format plan version the project is being saved. In Archicad 13 this can be only APIFType_PlanFile1200.
[out] A hash table to retrieve the converted module data.


Return Values

The function has completed with success.

For other common API errors see the API Errors document.



In order to save the add-on’s moduldata in the proper format into a previous version project file, you need to implement this callback function, and pass it to Archicad with ACAPI_Install_ModulDataSaveOldFormatHandler during the Initialize phase. It is also necessary to notify Archicad about this capability of the add-on by calling ACAPI_Register_ModulDataHandler from the RegisterInterface function.

This handler function is called whenever the user saves the project into an older format, and tha add-on has any moduldata stored currently into the project. The data should be constructed according to the required version into a dynamically allocated API_ModulData structure, and the pointer of this structure should be pushed into the modulesToSave table.
Notice that more modules can be added, should be identified with different names. In Archicad versions prior to 13 were able to store only one moduldata per add-on, this moduldata should be stored with empty string identifier (“”).

The memory allocated for the converted moduldata by the add-on’s handler function will be released by the caller application.

For further details of the notification process refer to the ModulData Manager section.



Registration and installing callback:

GSErrCode __ACENV_CALL  RegisterInterface (void)
    ACAPI_Register_ModulDataHandler ();
    return NoError;

GSErrCode __ACENV_CALL  Initialize (void)
    GSErrCode err = ACAPI_Install_ModulDataSaveOldFormatHandler (APIModulDataSaveAsOldFormat);
    return err;

Implementation of the handler function:

GSErrCode __ACENV_CALL  APIModulDataSaveAsOldFormat (API_FTypeID                                    planFileType,
                                                     GS::HashTable<GS::UniString, API_ModulData*>&  modulesToSave)
    GSErrCode err = NoError;

    if (planFileType == APIFType_PlanFile1200) {
        GS::Array<GS::UniString> modulNameList;
        ACAPI_ModulData_GetList (&modulNameList);

        USize nObjects = modulNameList.GetSize ();
        if (nObjects > 0) {
            API_ModulData* oldFormatModulData = new API_ModulData;  // must be allocated on the heap
            if (oldFormatModulData != nullptr) {
                BNZeroMemory (oldFormatModulData, sizeof (API_ModulData));
                oldFormatModulData->dataVersion = 0;
                oldFormatModulData->platformSign = GS::Act_Platform_Sign;
                oldFormatModulData->dataHdl = BMAllocateHandle (nObjects * sizeof (Int32), 0, 0);
                if (oldFormatModulData->dataHdl != nullptr) {
                    Int32* dataPtr = reinterpret_cast<Int32*> (*oldFormatModulData->dataHdl);
                    for (GS::Array<GS::UniString>::ConstIterator it = modulNameList.Enumerate (); it != nullptr; ++it) {
                        API_ModulData modulData;
                        BNZeroMemory (&modulData, sizeof (API_ModulData));
                        if (ACAPI_ModulData_Get (&modulData, *it) == NoError) {
                            *dataPtr = *(reinterpret_cast<Int32*> (*modulData.dataHdl));
                        BMKillHandle (&modulData.dataHdl);

                    modulesToSave.Put ("", oldFormatModulData);
                } else {
                    err = APIERR_MEMFULL;
        } else {
            err = APIERR_NOMODULEDATA;

    return err;

Refer to the ModulData Manager example add-on for more hints.



Version: API 13 or later
Header: APIdefs_Callback.h


See Also

ModulData Manager
API Functions