Close

Relief for ODA Team in Ukraine

Learn more
ODA IFC SDK
Work with BIM Collaboration Format

BIM Collaboration Format

The BIM Collaboration Format (BCF) enables various BIM applications to interact with each other by using materials that have been previously shared among project participants. This can be achieved by performing a file exchange between software platforms or using a service to connect these software platforms. BCF is a buildingSMART International open standard.

BCF provides data in XML format, which can include information about an issue in the form of comments, a reference to a view via a PNG image and camera settings for the attached IFC model, a reference to BIM elements via their IFC GUIDs, etc. Using BCF, you can easily identify and exchange model-based issues between BIM software tools, avoiding proprietary formats and workflows. The BCF-oriented workflow has a number of benefits in different situations, for example, during the design phase when you need to document QA/QC BIM items, during the construction phase when you need to track the availability of items or materials, and in many other cases. To get more information about BCF, see the BIM Collaboration Format article from buildingSMART International.

ODA IFC SDK supports a BCF file-based exchange. The file-based exchange workflow is relatively straightforward and popular among users. A BCF file (.bcfzip) is transferred from user to user, edited and returned. The public API for working with BCF is located at Ifc/Include/BCF. Here is an overview of the main elements:

  • odBcfInitialize() — Global function that loads the BCF module in memory.
  • odBcfUninitialize() — Global function that decreases the reference counter to the BCF module by 1 and unloads it from memory if the reference counter becomes equal to 0.
  • OdBcfDataAccessorXml — Class that provides access to BCF data in XML format, including all the data about the specified project, its folder, markup data, visualization information, etc.

For the full list of API items, see the OdBcf Namespace reference.

Examples of BCF Usage

The interaction between IFC SDK and BCF is implemented in multiple IFC example applications. The OpenIfcViewer application allows you to get a list of calculated collisions and save it into the BCF format (.bcfzip file). This file can be later opened by OpenIfcViewer via the BCF Manager tool to get information about each collision with details about an issue, set the author, add comments, and watch the collision with details focusing on the collided objects.

To get more information about OpenIfcViewer, visit https://openifcviewer.com/.

Other examples that implement interacting with BCF are ExBcf_2_1LoadFile and ExBcf_3_0LoadFile sample applications. Any of these applications loads a BCF file (version 2.1 or 3.0 respectively), prints information about its topics, and writes a new BCF file from an archive of the currently loaded .bcfzip file. Here is an overview of the functionality of these applications:

  1. Get console parameters. The first parameter is the name of a BCF file to read, the second parameter is the name of a BCF file to create, and the third parameter optionally specifies the working folder for BCF archive content.
    
    // create a service
    OdStaticRxObject< MyServices > svcs;
    
    OdString fileName = argv[1];
    OdString outFileName = argv[2];
    OdString workFolder = argc > 3 ? argv[3] : svcs.getTemporaryPath();
    
    
  2. Initialize the necessary modules. Note that to work with BCF, initialize the BCF module with the odBcfInitialize() function.
    
    /**********************************************************************/
    /* Initialize Runtime Extension environment                           */
    /**********************************************************************/
    odrxInitialize(&svcs);
    
    /**********************************************************************/
    /* Initialize BCF                                                     */
    /**********************************************************************/
    odBcfInitialize();
    
    
  3. Inside a try-catch block (for this and the following two steps), get the BCF data accessor and access the BCF archive where it retrieves the root folder (the try-catch block is omitted in the code for simplicity).
    
    OdBcf::OdBcfDataAccessorPtr pAccessor = OdBcf::OdBcfDataAccessorXml::createObject(workFolder);
    const OdBcf::OdBcfArchivePtr pArchive = pAccessor->getArchive(fileName);
    OdString rootDir = pArchive->getRootDir()->getFolder();
    
    
  4. Run through the topic folder, print its GUID, and for each topic get the topic title, GUID, author, priority, and the list of comments if there are any.
    
    const OdBcf::OdBcfTopicFolderMap& topicFolders = pArchive->getTopics();
    for (const auto &node : topicFolders)
    {
      OdString strGUID = node.first.toString();
      odifcPrintConsoleString(L"\nTopicFolder GUID: %s\n", strGUID.c_str());
    
      OdBcf::OdBcfTopicFolderPtr topicFolder = node.second;
    
      OdBcf::OdBcfMarkupPtr markup = topicFolder->getMarkup();
    
      const OdBcf::OdBcfTopicPtr topic = markup->getTopic();
      odifcPrintConsoleString(L" GUID: %s\n", topic->getGuid().toString().c_str());
      odifcPrintConsoleString(L" Title: %s\n", topic->getTitle().c_str());
      odifcPrintConsoleString(L" Author: %s\n", topic->getCreationAuthor().c_str());
      odifcPrintConsoleString(L" Priority: %s\n", topic->getPriority().c_str());
    
      const OdBcf::OdBcfCommentArray& comments = markup->getComment();
      if (comments.size() > 0)
      {
        odifcPrintConsoleString(L" Comments (%d):\n", comments.size());
        for (OdBcf::OdBcfCommentPtr comment : comments)
        {
          odifcPrintConsoleString(L" Comment (%s);\n", comment->getComment().c_str());
        }
      }
    
      odifcPrintConsoleString(L"==================================\n");
    }
    
    
  5. Try to write the contents of a currently open BCF file to a new BCF file with a given name.
    
    if (!outFileName.isEmpty())
    {
      odifcPrintConsoleString(L"Writing BCF Project to: %s...", outFileName.c_str());
      if (eOk == pAccessor->putArchive(outFileName, pArchive))
      {
        odifcPrintConsoleString(L" ok\n");
      }
      else
      {
        odifcPrintConsoleString(L" failed\n");
      }
    }
    
    
  6. Before exiting the main() function, uninitialize the modules and SDKs in reverse order. Before exiting the main() function, uninitialize the modules and SDKs in reverse order.
    
    /**********************************************************************/
    /* Uninitialize BCF                                                   */
    /**********************************************************************/
    odBcfUninitialize();
    
    /**********************************************************************/
    /* Uninitialize Runtime Extension environment                         */
    /**********************************************************************/
    ::odrxUninitialize();
    
    return 0;
    
    

Example of successful application execution:

See Also

ExBcf_2_1LoadFile Sample Application
ExBcf_3_0LoadFile Sample Application
OdBcf Namespace
Copyright © 2002 – 2022. Open Design Alliance. All rights reserved.