Пример #1
0
        internal static DxfBlock FromBuffer(DxfCodePairBufferReader buffer)
        {
            if (!buffer.ItemsRemain)
            {
                return null;
            }

            var block = new DxfBlock();
            var readingBlockStart = true;
            var readingBlockEnd = false;
            var entities = new List<DxfEntity>();
            while (buffer.ItemsRemain)
            {
                var pair = buffer.Peek();
                if (DxfCodePair.IsSectionEnd(pair))
                {
                    // done reading blocks
                    buffer.Advance(); // swallow (0, ENDSEC)
                    break;
                }
                else if (IsBlockStart(pair))
                {
                    if (readingBlockStart)
                    {
                        // if another block is found, stop reading this one because some blocks don't specify (0, ENDBLK)
                        break;
                    }

                    break;
                }
                else if (IsBlockEnd(pair))
                {
                    if (!readingBlockStart) throw new DxfReadException("Unexpected block end", pair);
                    readingBlockStart = false;
                    readingBlockEnd = true;
                    buffer.Advance(); // swallow (0, ENDBLK)
                }
                else if (pair.Code == 0)
                {
                    // should be an entity
                    var entity = DxfEntity.FromBuffer(buffer);
                    if (entity != null)
                    {
                        // entity could be null if it's unsupported
                        entities.Add(entity);
                    }
                }
                else
                {
                    // read value pair
                    if (readingBlockStart)
                    {
                        buffer.Advance();
                        switch (pair.Code)
                        {
                            case 1:
                                block.XrefName = pair.StringValue;
                                break;
                            case 2:
                                block.Name = pair.StringValue;
                                break;
                            case 3:
                                break;
                            case 4:
                                block.Description = pair.StringValue;
                                break;
                            case 5:
                                ((IDxfItemInternal)block).Handle = DxfCommonConverters.UIntHandle(pair.StringValue);
                                break;
                            case 8:
                                block.Layer = pair.StringValue;
                                break;
                            case 10:
                                block.BasePoint = block.BasePoint.WithUpdatedX(pair.DoubleValue);
                                break;
                            case 20:
                                block.BasePoint = block.BasePoint.WithUpdatedY(pair.DoubleValue);
                                break;
                            case 30:
                                block.BasePoint = block.BasePoint.WithUpdatedZ(pair.DoubleValue);
                                break;
                            case 67:
                                block.IsInPaperSpace = DxfCommonConverters.BoolShort(pair.ShortValue);
                                break;
                            case 70:
                                block.Flags = pair.ShortValue;
                                break;
                            case 330:
                                ((IDxfItemInternal)block).OwnerHandle = DxfCommonConverters.UIntHandle(pair.StringValue);
                                break;
                            case DxfCodePairGroup.GroupCodeNumber:
                                var groupName = DxfCodePairGroup.GetGroupName(pair.StringValue);
                                block.ExtensionDataGroups.Add(DxfCodePairGroup.FromBuffer(buffer, groupName));
                                break;
                            case (int)DxfXDataType.ApplicationName:
                                block.XData = DxfXData.FromBuffer(buffer, pair.StringValue);
                                break;
                        }
                    }
                    else if (readingBlockEnd)
                    {
                        block.EndBlock.ApplyCodePairs(buffer);
                    }
                    else
                    {
                        throw new DxfReadException("Unexpected pair in block", pair);
                    }
                }
            }

            var collected = DxfEntitiesSection.GatherEntities(entities);
            foreach (var entity in collected)
            {
                block.Entities.Add(entity);
            }

            return block;
        }
Пример #2
0
        public DxfFile ReadFile(BinaryReader reader)
        {
            // swallow next two characters
            var sub = reader.ReadChar();

            Debug.Assert(sub == 0x1A);
            var nul = reader.ReadChar();

            Debug.Assert(nul == 0x00);

            DxfPoint?blockBase    = null;
            var      entities     = new List <DxfEntity>();
            var      stillReading = true;
            Action <Func <BinaryReader, DxfEntity> > addEntity = (entityReader) =>
            {
                var entity = entityReader(reader);
                AssignCommonValues(entity);
                entities.Add(entity);
            };
            Func <DxfVertex> getLastVertex = () => entities.LastOrDefault() as DxfVertex;

            while (stillReading)
            {
                var itemType = (DxbItemType)reader.ReadByte();
                switch (itemType)
                {
                case DxbItemType.Line:
                    addEntity(ReadLine);
                    break;

                case DxbItemType.Point:
                    addEntity(ReadPoint);
                    break;

                case DxbItemType.Circle:
                    addEntity(ReadCircle);
                    break;

                case DxbItemType.Arc:
                    addEntity(ReadArc);
                    break;

                case DxbItemType.Trace:
                    addEntity(ReadTrace);
                    break;

                case DxbItemType.Solid:
                    addEntity(ReadSolid);
                    break;

                case DxbItemType.Seqend:
                    addEntity(ReadSeqend);
                    break;

                case DxbItemType.Polyline:
                    addEntity(ReadPolyline);
                    break;

                case DxbItemType.Vertex:
                    addEntity(ReadVertex);
                    break;

                case DxbItemType.Face:
                    addEntity(ReadFace);
                    break;

                case DxbItemType.ScaleFactor:
                    _scaleFactor = ReadF(reader);
                    break;

                case DxbItemType.NewLayer:
                    var sb = new StringBuilder();
                    for (int b = reader.ReadByte(); b != 0; b = reader.ReadByte())
                    {
                        sb.Append((char)b);
                    }
                    _layerName = sb.ToString();
                    break;

                case DxbItemType.LineExtension:
                    addEntity(ReadLineExtension);
                    break;

                case DxbItemType.TraceExtension:
                    addEntity(ReadTraceExtension);
                    break;

                case DxbItemType.BlockBase:
                    var x = ReadN(reader);
                    var y = ReadN(reader);
                    if (blockBase == null && entities.Count == 0)
                    {
                        // only if this is the first item encountered
                        blockBase = new DxfPoint(x, y, 0.0);
                    }
                    break;

                case DxbItemType.Bulge:
                {
                    var bulge      = ReadU(reader);
                    var lastVertex = getLastVertex();
                    if (lastVertex != null)
                    {
                        lastVertex.Bulge = bulge;
                    }
                }
                break;

                case DxbItemType.Width:
                {
                    var startWidth = ReadN(reader);
                    var endWidth   = ReadN(reader);
                    var lastVertex = getLastVertex();
                    if (lastVertex != null)
                    {
                        lastVertex.StartingWidth = startWidth;
                        lastVertex.EndingWidth   = endWidth;
                    }
                }
                break;

                case DxbItemType.NumberMode:
                    _isIntegerMode = ReadW(reader) == 0;
                    break;

                case DxbItemType.NewColor:
                    _color = DxfColor.FromRawValue((short)ReadW(reader));
                    break;

                case DxbItemType.LineExtension3D:
                    addEntity(ReadLineExtension3D);
                    break;

                case 0:
                    stillReading = false;
                    break;
                }
            }

            var file = new DxfFile();

            foreach (var section in file.Sections)
            {
                section.Clear();
            }

            // collect the entities (e.g., polylines, etc.)
            entities = DxfEntitiesSection.GatherEntities(entities);

            if (blockBase != null)
            {
                // entities are all contained in a block
                var block = new DxfBlock();
                block.BasePoint = blockBase.GetValueOrDefault();
                foreach (var entity in entities)
                {
                    block.Entities.Add(entity);
                }

                file.Blocks.Add(block);
            }
            else
            {
                // just a normal collection of entities
                foreach (var entity in entities)
                {
                    file.Entities.Add(entity);
                }
            }

            return(file);
        }