public static IStepFileHeader LoadStep21Header(Stream stream) { var header = new StepFileHeader(StepFileHeader.HeaderCreationMode.LeaveEmpty, null); var scanner = new XbimP21Scanner(stream, 1000); scanner.EntityCreate += (string name, long?label, bool inHeader) => { if (inHeader) { switch (name) { case "FILE_DESCRIPTION": return(header.FileDescription); case "FILE_NAME": return(header.FileName); case "FILE_SCHEMA": if (header.FileSchema != null) { //set to new schema if it was set before from EntityFactory data header.FileSchema = new StepFileSchema(); } return(header.FileSchema); default: return(null); } } else { return(null); } }; try { scanner.Parse(true); } catch (Exception e) { var position = scanner.CurrentPosition; throw new XbimParserException(string.Format("Parser failed on line {0}, column {1}", position.EndLine, position.EndColumn), e); } return(header); }
protected virtual int LoadStep21(XbimP21Scanner parser) { if (Header == null) { Header = new StepFileHeader(StepFileHeader.HeaderCreationMode.LeaveEmpty, this); } if (EntityFactory == null && _factoryResolver == null) { throw new XbimParserException("EntityFactory is not defined and no resolver is specified to create one. Data can't be created."); } parser.EntityCreate += (string name, long?label, bool header) => { if (header) { switch (name) { case "FILE_DESCRIPTION": return(Header.FileDescription); case "FILE_NAME": return(Header.FileName); case "FILE_SCHEMA": if (Header.FileSchema != null) { //set to new schema if it was set before from EntityFactory data Header.FileSchema = new StepFileSchema(); } return(Header.FileSchema); default: return(null); } } if (EntityFactory == null) { EntityFactory = _factoryResolver(Header.FileSchema.Schemas); if (EntityFactory == null) { throw new XbimParserException($"Entity factory resolver didn't resolve factory for schema '{string.Join(", ", Header.FileSchema.Schemas)}'"); } InitFromEntityFactory(EntityFactory); } if (label == null) { return(EntityFactory.New(name)); } var ent = EntityFactory.New(this, name, (int)label, true); // if entity is null do not add so that the file load operation can survive an illegal entity // e.g. an abstract class instantiation. if (ent != null) { _instances.InternalAdd(ent); } else { var msg = $"Error in file at label {label} for type {name}."; if (Metadata.ExpressType(name).Type.GetTypeInfo().IsAbstract) { msg = string.Format("Illegal element in file; cannot instantiate the abstract type {0} at label {1}.", name, label); } Logger?.LogError(msg); } //make sure that new added entities will have higher labels to avoid any clashes if (label >= _instances.CurrentLabel) { _instances.CurrentLabel = (int)label; } return(ent); }; try { parser.Parse(); //fix header with the schema if it was not a part of the data if (Header.FileSchema.Schemas.Count == 0) { foreach (var s in EntityFactory.SchemasIds) { Header.FileSchema.Schemas.Add(s); } } } catch (Exception e) { var position = parser.CurrentPosition; throw new XbimParserException(string.Format("Parser failed on line {0}, column {1}", position.EndLine, position.EndColumn), e); } // if the model is empty, having just a header, entity factory might still be empty if (EntityFactory == null) { EntityFactory = _factoryResolver(Header.FileSchema.Schemas); if (EntityFactory == null) { throw new XbimParserException($"Entity factory resolver didn't resolve factory for schema '{string.Join(", ", Header.FileSchema.Schemas)}'"); } InitFromEntityFactory(EntityFactory); } //fix case if necessary for (int i = 0; i < Header.FileSchema.Schemas.Count; i++) { var id = Header.FileSchema.Schemas[i]; var sid = EntityFactory.SchemasIds.FirstOrDefault(s => id.StartsWith(s, StringComparison.OrdinalIgnoreCase)); if (sid == null) { //add in a bit of flexibility for old Ifc models with weird schema names var old2xSchemaNamesThatAreOK = new[] { "IFC2X2_FINAL", "IFC2X2" }; if (old2xSchemaNamesThatAreOK.FirstOrDefault(s => string.Equals(s, id, StringComparison.OrdinalIgnoreCase)) == null) { throw new XbimParserException("Mismatch between schema defined in the file and schemas available in the data model."); } else { sid = EntityFactory.SchemasIds.FirstOrDefault(s => string.Equals(s, "IFC2X3", StringComparison.OrdinalIgnoreCase)); } } //if the case is different set it to the one from entity factory if (id != sid) { Header.FileSchema.Schemas[i] = sid; } } return(parser.ErrorCount); }