Describe IfcOpenShell python architecture in the developer guide

This commit is contained in:
Dion Moult
2021-07-01 11:17:59 +10:00
parent 733b7c0e1e
commit a1032a3bf0
3 changed files with 105 additions and 7 deletions
@@ -17,7 +17,9 @@ schema in memory. Every user operation reads or writes this data structure in
memory, and the IFC data becomes the source of truth for all data. There is no
such thing as an import or export, but simply a serialisation or deserialisation
operation. This also means that the ``.blend`` container is largely unnecessary,
as nothing of significance is stored in the Blender system.
as nothing of significance is stored in the Blender system. Unlike traditional
BIM which relies on translated IFC data, the BlenderBIM Add-on works with Native
IFC, and also works equally across all disciplines.
Due to this significant difference, hacking on the BlenderBIM Add-on requires
knowledge not just about how Blender works, but also how IFC works.
@@ -75,7 +77,106 @@ user settings.
Of course, there are many details that we are glossing over, but it provides a
good representation of data flow in the BlenderBIM Add-on.
Code structure
--------------
IfcOpenShell Architecture
-------------------------
TODO
Manipulating IFC data is not simple. IFC may be serialised into multiple
formats, multiple schema versions must be supported, and geometry may be defined
in a highly parametric or implicit manner, which geometry kernels do not
natively support. All this heavy lifting is performed by the IfcOpenShell
library.
The IfcOpenShell library consists of a C++ based core. Its geometry processing
is done using OpenCascade, and optionally CGAL as an experimental option. By the
time the BlenderBIM Add-on interacts with IFC, it uses the IfcOpenShell Python
bindings, so all IFC data is already deserialised into Python objects. The inner
workings of the C++ base is out of scope.
.. image:: ifcopenshell-architecture.png
..
digraph G {rankdir=LR;
node [fontname = "Handlee", shape=rect, style=filled,color=pink];
IfcOpenShell [label="IfcOpenShell C++", color=grey]
ifcopenshell [label="IfcOpenShell-python"]
OpenCascade [color=grey]
CGAL [color=grey]
OpenCascade -> IfcOpenShell
CGAL -> IfcOpenShell
IfcOpenShell -> ifcopenshell
ifcopenshell -> Core
ifcopenshell -> Utils
ifcopenshell -> API
API -> Module01
API -> Module02
API -> Module03
Module03[label="..."]
Module01 -> Data
Module01 -> Usecase
}
IfcOpenShell offers a core set of low-level functionality to read and write this
data. An example of the core functionality would be:
.. code-block:: python
import ifcopenshell
model = ifcopenshell.open("foo.ifc")
wall = model.create_entity("IfcWall")
wall.Name = "Foobar"
Core functions are simple read and write operations with no post processing.
Core functions also include geometry processing, which converts IFC geometry
into OpenCascade objects.
Sometimes, there are repetitive actions that need to be performed. These
functions are grouped into a ``util`` module. These include utility functions
for coordinate calculations, date conversions, filtering elements, unit
conversions, and more. Utility functions make no assumption about the context in
which they are used, and so perform highly specific tasks and nothing else.
Here's an example of utility functionality:
.. code-block:: python
import ifcopenshell
import ifcopenshell.util.date
import ifcopenshell.util.geolocation
start = ifcopenshell.util.date.ifc2datetime(task_time.ScheduleStart)
coordinates = ifcopenshell.util.geolocation.local2global(matrix, eastings, ...)
When authoring, core and utility functions are usually too low-level. To cater
for this, a high level API is provided. The API is divided into mostly isolated
modules, each module representing a distinct set of concepts in the IFC schema.
Unlike the util module, these API modules are highly context-sensitive, and
assume that you intend to be authoring native IFC.
This context-sensitive assumption means that the functions within the modules
are designed around typical usecases in an authoring environment. It performs
all the necessary manipulations to achieve a domain-specific usecase. Authoring
is complex and requires a deep knowledge of IFC to perform correctly and ensure
that the IFC graph state is well maintained. Typically, any authoring operation
that does not use the API is likely to contain mistakes.
Each module contains a Data class to extract various IFC data related to the IFC
concept that the module relates to. The ``Data`` classes parse the complex IFC
graph and convert it into a cache of primitive Python data. The ``Usecase``
clases perform a defined user operation. Here's an example of it in action:
.. code-block:: python
import ifcopenshell.api
ifcopenshell.api.run("grid.create_grid_axis", model, ...)
ifcopenshell.api.run("structural.add_structural_load", model, ...)
Because the API performs all the IFC manipulations to achieve a usecase, no
further interaction is required in a typical native IFC authoring environment.
For this reason, the BlenderBIM Add-on only interacts with the API for its
authoring capabilities.
The code for IfcOpenShell's various systems can be found here:
- `ifcopenshell (core) <https://github.com/IfcOpenShell/IfcOpenShell/tree/v0.6.0/src/ifcopenshell-python/ifcopenshell>`__
- `ifcopenshell.util <https://github.com/IfcOpenShell/IfcOpenShell/tree/v0.6.0/src/ifcopenshell-python/ifcopenshell/util>`__
- `ifcopenshell.api <https://github.com/IfcOpenShell/IfcOpenShell/tree/v0.6.0/src/ifcopenshell-python/ifcopenshell/api>`__
Binary file not shown.

After

Width:  |  Height:  |  Size: 408 KiB

@@ -142,9 +142,6 @@ Required static assets are:
bim/data/gantt/jsgantt.js (from jsgantt-improved)
bim/data/gantt/jsgantt.css (from jsgantt-improved)
If you receive an error when enabling the add-on, you may have installed the
package for the wrong platform.
Source installation
-------------------