|
@@ -882,6 +882,7 @@ void ProcessSpatialStructures(ConversionData& conv)
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+ std::vector<aiNode*> nodes;
|
|
|
|
|
|
for(const STEP::LazyObject* lz : *range) {
|
|
|
const IfcSpatialStructureElement* const prod = lz->ToPtr<IfcSpatialStructureElement>();
|
|
@@ -890,20 +891,19 @@ void ProcessSpatialStructures(ConversionData& conv)
|
|
|
}
|
|
|
IFCImporter::LogDebug("looking at spatial structure `" + (prod->Name ? prod->Name.Get() : "unnamed") + "`" + (prod->ObjectType? " which is of type " + prod->ObjectType.Get():""));
|
|
|
|
|
|
- // the primary site is referenced by an IFCRELAGGREGATES element which assigns it to the IFCPRODUCT
|
|
|
+ // the primary sites are referenced by an IFCRELAGGREGATES element which assigns them to the IFCPRODUCT
|
|
|
const STEP::DB::RefMap& refs = conv.db.GetRefs();
|
|
|
- STEP::DB::RefMapRange range = refs.equal_range(conv.proj.GetID());
|
|
|
- for(;range.first != range.second; ++range.first) {
|
|
|
- if(const IfcRelAggregates* const aggr = conv.db.GetObject((*range.first).second)->ToPtr<IfcRelAggregates>()) {
|
|
|
+ STEP::DB::RefMapRange ref_range = refs.equal_range(conv.proj.GetID());
|
|
|
+ for(; ref_range.first != ref_range.second; ++ref_range.first) {
|
|
|
+ if(const IfcRelAggregates* const aggr = conv.db.GetObject((*ref_range.first).second)->ToPtr<IfcRelAggregates>()) {
|
|
|
|
|
|
for(const IfcObjectDefinition& def : aggr->RelatedObjects) {
|
|
|
// comparing pointer values is not sufficient, we would need to cast them to the same type first
|
|
|
// as there is multiple inheritance in the game.
|
|
|
if (def.GetID() == prod->GetID()) {
|
|
|
IFCImporter::LogDebug("selecting this spatial structure as root structure");
|
|
|
- // got it, this is the primary site.
|
|
|
- conv.out->mRootNode = ProcessSpatialStructure(NULL,*prod,conv,NULL);
|
|
|
- return;
|
|
|
+ // got it, this is one primary site.
|
|
|
+ nodes.push_back(ProcessSpatialStructure(NULL, *prod, conv, NULL));
|
|
|
}
|
|
|
}
|
|
|
|
|
@@ -911,19 +911,42 @@ void ProcessSpatialStructures(ConversionData& conv)
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+ size_t nb_nodes = nodes.size();
|
|
|
|
|
|
- IFCImporter::LogWarn("failed to determine primary site element, taking the first IfcSite");
|
|
|
- for(const STEP::LazyObject* lz : *range) {
|
|
|
- const IfcSpatialStructureElement* const prod = lz->ToPtr<IfcSpatialStructureElement>();
|
|
|
- if(!prod) {
|
|
|
- continue;
|
|
|
- }
|
|
|
+ if (nb_nodes == 0) {
|
|
|
+ IFCImporter::LogWarn("failed to determine primary site element, taking all the IfcSite");
|
|
|
+ for (const STEP::LazyObject* lz : *range) {
|
|
|
+ const IfcSpatialStructureElement* const prod = lz->ToPtr<IfcSpatialStructureElement>();
|
|
|
+ if (!prod) {
|
|
|
+ continue;
|
|
|
+ }
|
|
|
|
|
|
- conv.out->mRootNode = ProcessSpatialStructure(NULL,*prod,conv,NULL);
|
|
|
- return;
|
|
|
- }
|
|
|
+ nodes.push_back(ProcessSpatialStructure(NULL, *prod, conv, NULL));
|
|
|
+ }
|
|
|
+
|
|
|
+ nb_nodes = nodes.size();
|
|
|
+ }
|
|
|
+
|
|
|
+ if (nb_nodes == 1) {
|
|
|
+ conv.out->mRootNode = nodes[0];
|
|
|
+ }
|
|
|
+ else if (nb_nodes > 1) {
|
|
|
+ conv.out->mRootNode = new aiNode("Root");
|
|
|
+ conv.out->mRootNode->mParent = NULL;
|
|
|
+ conv.out->mRootNode->mNumChildren = static_cast<unsigned int>(nb_nodes);
|
|
|
+ conv.out->mRootNode->mChildren = new aiNode*[conv.out->mRootNode->mNumChildren];
|
|
|
+
|
|
|
+ for (size_t i = 0; i < nb_nodes; ++i) {
|
|
|
+ aiNode* node = nodes[i];
|
|
|
+
|
|
|
+ node->mParent = conv.out->mRootNode;
|
|
|
|
|
|
- IFCImporter::ThrowException("failed to determine primary site element");
|
|
|
+ conv.out->mRootNode->mChildren[i] = node;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ else {
|
|
|
+ IFCImporter::ThrowException("failed to determine primary site element");
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
// ------------------------------------------------------------------------------------------------
|