/// <summary>
        /// Adds openings to an element.
        /// </summary>
        /// <param name="exporterIFC">The exporter.</param>
        /// <param name="elementHandles">The parent handles.</param>
        /// <param name="curveLoops">The parent CurveLoops.</param>
        /// <param name="element">The element.</param>
        /// <param name="lcs">The local coordinate system.</param>
        /// <param name="scaledWidth">The width.</param>
        /// <param name="range">The range.</param>
        /// <param name="setter">The placement setter.</param>
        /// <param name="localPlacement">The local placement.</param>
        /// <param name="localWrapper">The wrapper.</param>
        public static void AddOpeningsToElement(ExporterIFC exporterIFC, IList<IFCAnyHandle> elementHandles,
            IList<CurveLoop> curveLoops, Element element, Transform lcs, double scaledWidth,
            IFCRange range, PlacementSetter setter, IFCAnyHandle localPlacement, ProductWrapper localWrapper)
        {
            IList<IFCOpeningData> openingDataList = ExporterIFCUtils.GetOpeningData(exporterIFC, element, lcs, range);
             IFCFile file = exporterIFC.GetFile();
             IFCAnyHandle ownerHistory = ExporterCacheManager.OwnerHistoryHandle;
             foreach (IFCOpeningData openingData in openingDataList)
             {
            Element openingElem = element.Document.GetElement(openingData.OpeningElementId);
            if (openingElem == null)
               openingElem = element;

            bool currentWallIsHost = false;
            FamilyInstance openingFInst = openingElem as FamilyInstance;
            if (openingFInst != null && openingFInst.Host != null)
            {
               if (openingFInst.Host.Id == element.Id)
                  currentWallIsHost = true;
                  //continue;      // If the host is not the current Wall, skip this opening
            }

            // Don't export the opening if WallSweep category has been turned off.
            // This is currently restricted to WallSweeps because the element responsible for the opening could be a variety of things,
            // including a line as part of the elevation profile of the wall.
            // As such, we will restrict which element types we check for CanExportElement.
            if ((openingElem is WallSweep) && (!ElementFilteringUtil.CanExportElement(exporterIFC, openingElem, true)))
               continue;

            IList<IFCExtrusionData> extrusionDataList = openingData.GetExtrusionData();
            IFCAnyHandle parentHandle = null;
            if (elementHandles.Count > 1 && extrusionDataList.Count > 0)
            {
               parentHandle = FindParentHandle(elementHandles, curveLoops, extrusionDataList[0].GetLoops()[0]);
            }

            if (parentHandle == null)
               parentHandle = elementHandles[0];

            bool isDoorOrWindowOpening = IsDoorOrWindowOpening(exporterIFC, openingElem, element);
            bool insertHasHost = false;
            bool insertInThisHost = false;
            if (openingElem is FamilyInstance && element is Wall)
            {
               string ifcEnumType;
               IFCExportInfoPair exportType = ExporterUtil.GetExportType(exporterIFC, openingElem, out ifcEnumType);
               Element instHost = (openingElem as FamilyInstance).Host;
               insertHasHost = (instHost != null);
               insertInThisHost = (insertHasHost && instHost.Id == element.Id);
               isDoorOrWindowOpening =
                  insertInThisHost &&
                  (exportType.ExportInstance == IFCEntityType.IfcDoor ||
                  exportType.ExportType == IFCEntityType.IfcDoorType ||
                  exportType.ExportInstance == IFCEntityType.IfcWindow ||
                  exportType.ExportType == IFCEntityType.IfcWindowType);
            }

            if (isDoorOrWindowOpening && currentWallIsHost)
            {
               DoorWindowDelayedOpeningCreator delayedCreator =
                   DoorWindowDelayedOpeningCreator.Create(exporterIFC, openingData, scaledWidth, element.Id, parentHandle, setter.LevelId);
               if (delayedCreator != null)
               {
                  ExporterCacheManager.DoorWindowDelayedOpeningCreatorCache.Add(delayedCreator);
                  continue;
               }
            }

            // If the opening is "filled" by another element (either a door or window as
            // determined above, or an embedded wall, then we can't use the element GUID
            // for the opening.
            bool canUseElementGUID = (!insertHasHost || insertInThisHost) &&
               !isDoorOrWindowOpening &&
               !(openingElem is Wall);

            IList<Solid> solids = openingData.GetOpeningSolids();
            foreach (Solid solid in solids)
            {
               using (IFCExtrusionCreationData extrusionCreationData = new IFCExtrusionCreationData())
               {
                  extrusionCreationData.SetLocalPlacement(ExporterUtil.CreateLocalPlacement(file, localPlacement, null));
                  extrusionCreationData.ReuseLocalPlacement = true;

                  string openingGUID = CreateOpeningGUID(openingElem, canUseElementGUID);
                  canUseElementGUID = false; // Either it was used above, and therefore is now false, or it was already false.

                  CreateOpening(exporterIFC, parentHandle, element, openingElem, openingGUID, solid, scaledWidth, openingData.IsRecess, extrusionCreationData,
                      setter, localWrapper);
               }
            }

            foreach (IFCExtrusionData extrusionData in extrusionDataList)
            {
               if (extrusionData.ScaledExtrusionLength < MathUtil.Eps())
                  extrusionData.ScaledExtrusionLength = scaledWidth;

               string openingGUID = CreateOpeningGUID(openingElem, canUseElementGUID);
               canUseElementGUID = false; // Either it was used above, and therefore is now false, or it was already false.

               CreateOpening(exporterIFC, parentHandle, localPlacement, element, openingElem, openingGUID, extrusionData, lcs, openingData.IsRecess,
                   setter, localWrapper);
            }
             }
        }
Exemple #2
0
        /// <summary>
        /// Adds openings to an element.
        /// </summary>
        /// <param name="exporterIFC">The exporter.</param>
        /// <param name="elementHandles">The parent handles.</param>
        /// <param name="curveLoops">The parent CurveLoops.</param>
        /// <param name="element">The element.</param>
        /// <param name="plane">The plane.</param>
        /// <param name="scaledWidth">The width.</param>
        /// <param name="range">The range.</param>
        /// <param name="setter">The placement setter.</param>
        /// <param name="localPlacement">The local placement.</param>
        /// <param name="localWrapper">The wrapper.</param>
        public static void AddOpeningsToElement(ExporterIFC exporterIFC, IList <IFCAnyHandle> elementHandles, IList <CurveLoop> curveLoops, Element element, Plane plane, double scaledWidth,
                                                IFCRange range, PlacementSetter setter, IFCAnyHandle localPlacement, ProductWrapper localWrapper)
        {
            IList <IFCOpeningData> openingDataList = ExporterIFCUtils.GetOpeningData(exporterIFC, element, plane, range);
            IFCFile      file         = exporterIFC.GetFile();
            IFCAnyHandle ownerHistory = exporterIFC.GetOwnerHistoryHandle();

            foreach (IFCOpeningData openingData in openingDataList)
            {
                Element openingElem = element.Document.GetElement(openingData.OpeningElementId);
                if (openingElem == null)
                {
                    openingElem = element;
                }

                // Don't export the opening if WallSweep category has been turned off.
                // This is currently restricted to WallSweeps because the element responsible for the opening could be a variety of things, including a line as part of the elevation profile of the wall.
                // As such, we will restrict which element types we check for CanExportElement.
                if ((openingElem is WallSweep) && (!ElementFilteringUtil.CanExportElement(exporterIFC, openingElem, true)))
                {
                    continue;
                }

                IList <IFCExtrusionData> extrusionDataList = openingData.GetExtrusionData();
                IFCAnyHandle             parentHandle      = null;
                if (elementHandles.Count > 1 && extrusionDataList.Count > 0)
                {
                    parentHandle = FindParentHandle(elementHandles, curveLoops, extrusionDataList[0].GetLoops()[0]);
                }

                if (parentHandle == null)
                {
                    parentHandle = elementHandles[0];
                }

                bool isDoorOrWindowOpening = IsDoorOrWindowOpening(exporterIFC, openingElem, element);
                if (isDoorOrWindowOpening)
                {
                    DoorWindowDelayedOpeningCreator delayedCreator =
                        DoorWindowDelayedOpeningCreator.Create(exporterIFC, openingData, scaledWidth, element.Id, parentHandle, setter.LevelId);
                    if (delayedCreator != null)
                    {
                        ExporterCacheManager.DoorWindowDelayedOpeningCreatorCache.Add(delayedCreator);
                        continue;
                    }
                }

                bool canUseElementGUID = !isDoorOrWindowOpening;

                IList <Solid> solids = openingData.GetOpeningSolids();
                foreach (Solid solid in solids)
                {
                    using (IFCExtrusionCreationData extrusionCreationData = new IFCExtrusionCreationData())
                    {
                        extrusionCreationData.SetLocalPlacement(ExporterUtil.CreateLocalPlacement(file, localPlacement, null));
                        extrusionCreationData.ReuseLocalPlacement = true;

                        string openingGUID = null;
                        if (canUseElementGUID)
                        {
                            openingGUID       = GUIDUtil.CreateGUID(openingElem);
                            canUseElementGUID = false;
                        }
                        else
                        {
                            openingGUID = GUIDUtil.CreateGUID();
                        }
                        CreateOpening(exporterIFC, parentHandle, element, openingElem, openingGUID, solid, scaledWidth, openingData.IsRecess, extrusionCreationData,
                                      setter, localWrapper);
                    }
                }

                foreach (IFCExtrusionData extrusionData in extrusionDataList)
                {
                    if (extrusionData.ScaledExtrusionLength < MathUtil.Eps())
                    {
                        extrusionData.ScaledExtrusionLength = scaledWidth;
                    }

                    string openingGUID = null;
                    if (canUseElementGUID)
                    {
                        openingGUID       = GUIDUtil.CreateGUID(element);
                        canUseElementGUID = false;
                    }
                    else
                    {
                        openingGUID = GUIDUtil.CreateGUID();
                    }
                    CreateOpening(exporterIFC, parentHandle, localPlacement, element, openingElem, openingGUID, extrusionData, plane, openingData.IsRecess,
                                  setter, localWrapper);
                }
            }
        }
Exemple #3
0
        /// <summary>
        /// Adds openings to an element.
        /// </summary>
        /// <param name="exporterIFC">The exporter.</param>
        /// <param name="elementHandles">The parent handles.</param>
        /// <param name="curveLoops">The parent CurveLoops.</param>
        /// <param name="element">The element.</param>
        /// <param name="lcs">The local coordinate system.</param>
        /// <param name="scaledWidth">The width.</param>
        /// <param name="range">The range.</param>
        /// <param name="setter">The placement setter.</param>
        /// <param name="localPlacement">The local placement.</param>
        /// <param name="localWrapper">The wrapper.</param>
        public static void AddOpeningsToElement(ExporterIFC exporterIFC,
                                                IList <IFCAnyHandle> elementHandles, IList <CurveLoop> curveLoops, Element element,
                                                Transform lcs, double scaledWidth, IFCRange range, PlacementSetter setter,
                                                IFCAnyHandle localPlacement, ProductWrapper localWrapper)
        {
            if (lcs == null && ((curveLoops?.Count ?? 0) > 0))
            {
                // assumption: first curve loop defines the plane.
                Plane hostObjPlane = curveLoops[0].HasPlane() ? curveLoops[0].GetPlane(): null;

                if (hostObjPlane != null)
                {
                    lcs = GeometryUtil.CreateTransformFromPlane(hostObjPlane);
                }
            }

            IList <IFCOpeningData> openingDataList = ExporterIFCUtils.GetOpeningData(exporterIFC,
                                                                                     element, lcs, range);
            IFCFile file = exporterIFC.GetFile();

            int openingIndex = 0;

            foreach (IFCOpeningData openingData in openingDataList)
            {
                openingIndex++;

                Element openingElem = element.Document.GetElement(openingData.OpeningElementId);
                if (openingElem == null)
                {
                    openingElem = element;
                }

                bool           currentWallIsHost = false;
                FamilyInstance openingFInst      = openingElem as FamilyInstance;
                if (openingFInst != null && openingFInst.Host != null)
                {
                    if (openingFInst.Host.Id == element.Id)
                    {
                        currentWallIsHost = true;
                    }
                }

                // Don't export the opening if WallSweep category has been turned off.
                // This is currently restricted to WallSweeps because the element responsible for the opening could be a variety of things,
                // including a line as part of the elevation profile of the wall.
                // As such, we will restrict which element types we check for CanExportElement.
                if ((openingElem is WallSweep) &&
                    (!ElementFilteringUtil.CanExportElement(exporterIFC, openingElem, true)))
                {
                    continue;
                }

                IList <IFCExtrusionData> extrusionDataList = openingData.GetExtrusionData();
                IFCAnyHandle             parentHandle      = FindParentHandle(elementHandles, curveLoops, extrusionDataList);

                string            predefinedType;
                IFCExportInfoPair exportType = ExporterUtil.GetProductExportType(exporterIFC,
                                                                                 openingElem, out predefinedType);
                bool exportingDoorOrWindow = (exportType.ExportInstance == IFCEntityType.IfcDoor ||
                                              exportType.ExportType == IFCEntityType.IfcDoorType ||
                                              exportType.ExportInstance == IFCEntityType.IfcWindow ||
                                              exportType.ExportType == IFCEntityType.IfcWindowType);

                bool isDoorOrWindowOpening = IsDoorOrWindowOpening(openingElem, element,
                                                                   exportingDoorOrWindow);

                if (isDoorOrWindowOpening && currentWallIsHost)
                {
                    DoorWindowDelayedOpeningCreator delayedCreator =
                        DoorWindowDelayedOpeningCreator.Create(exporterIFC, openingData, scaledWidth,
                                                               element.Id, parentHandle, setter.LevelId);
                    if (delayedCreator != null)
                    {
                        ExporterCacheManager.DoorWindowDelayedOpeningCreatorCache.Add(delayedCreator);
                        continue;
                    }
                }

                IList <Solid> solids     = openingData.GetOpeningSolids();
                int           solidIndex = 0;
                foreach (Solid solid in solids)
                {
                    solidIndex++;

                    using (IFCExtrusionCreationData extrusionCreationData = new IFCExtrusionCreationData())
                    {
                        extrusionCreationData.SetLocalPlacement(ExporterUtil.CreateLocalPlacement(file, localPlacement, null));
                        extrusionCreationData.ReuseLocalPlacement = true;

                        string openingGUID = CreateOpeningGUID(openingElem, range, openingIndex, solidIndex);

                        CreateOpening(exporterIFC, parentHandle, element, openingElem, openingGUID, solid, scaledWidth, openingData.IsRecess, extrusionCreationData,
                                      setter, localWrapper);
                    }
                }

                foreach (IFCExtrusionData extrusionData in extrusionDataList)
                {
                    solidIndex++;

                    if (extrusionData.ScaledExtrusionLength < MathUtil.Eps())
                    {
                        extrusionData.ScaledExtrusionLength = scaledWidth;
                    }

                    string openingGUID = CreateOpeningGUID(openingElem, range, openingIndex, solidIndex);

                    CreateOpening(exporterIFC, parentHandle, localPlacement, element, openingElem,
                                  openingGUID, extrusionData, lcs, openingData.IsRecess, setter, localWrapper);
                }
            }
        }