Example #1
0
        /// <summary>
        /// Processes any new blocks that have been pushed to <see cref="NewBlocks"/>.
        /// </summary>
        /// <param name="result">The last result of matching.</param>
        /// <param name="allowClosing">if set to <c>true</c> the processing of a new block will close existing opened blocks].</param>
        /// <exception cref="InvalidOperationException">The NewBlocks is not empty. This is happening if a LeafBlock is not the last to be pushed</exception>
        private void ProcessNewBlocks(BlockState result, bool allowClosing)
        {
            var newBlocks = NewBlocks;

            while (newBlocks.Count > 0)
            {
                var block = newBlocks.Pop();

                if (block.Parser == null)
                {
                    ThrowHelper.InvalidOperationException($"The new block [{block.GetType()}] must have a valid Parser property");
                }

                block.Line = LineIndex;

                // If we have a leaf block
                var leaf = block as LeafBlock;
                if (leaf != null)
                {
                    if (!result.IsDiscard())
                    {
                        leaf.AppendLine(ref Line, Column, LineIndex, CurrentLineStartPosition);
                    }

                    if (newBlocks.Count > 0)
                    {
                        ThrowHelper.InvalidOperationException(
                            "The NewBlocks is not empty. This is happening if a LeafBlock is not the last to be pushed");
                    }
                }

                if (allowClosing)
                {
                    // Close any previous blocks not opened
                    CloseAll(false);
                }

                // If previous block is a container, add the new block as a children of the previous block
                if (block.Parent == null)
                {
                    UpdateLastBlockAndContainer();
                    CurrentContainer.Add(block);
                }

                block.IsOpen = result.IsContinue();

                // Add a block BlockProcessor to the stack (and leave it opened)
                OpenedBlocks.Add(block);

                if (leaf != null)
                {
                    ContinueProcessingLine = false;
                    return;
                }
            }

            ContinueProcessingLine = !result.IsDiscard();
        }