GAM456-SpaceInvaders / SpaceInvaders / 5_Composite / ForwardIterator.cs
ForwardIterator.cs
Raw
using System;
using System.Diagnostics;


namespace SpaceInvaders
{
    public class ForwardIterator : TreeIterator
    {
        //-------------------------------------------------------------------
        //  FIELDS
        //-------------------------------------------------------------------

        private Component pCurr;
        private Component pRoot;


        //-------------------------------------------------------------------
        //  CLASS METHODS
        //-------------------------------------------------------------------

        public ForwardIterator(Component pStart)
        {
            Debug.Assert(pStart != null);
            Debug.Assert(pStart.type == Component.Type.Composite);

            this.pCurr = pStart;
            this.pRoot = pStart;
        }

        //help step through tree
        private Component NextStep(Component pNode, Component pParent, Component pChild, Component pSibling)
        {
            pNode = null;

            //we start at the bottom
            if (pChild != null)
            {
                pNode = pChild;
            }
            //go up a level
            else
            {
                //else, we start here
                if(pSibling != null)
                {
                    pNode = pSibling;
                }
                //else, go up to parent
                else
                {
                    while(pParent != null)
                    {
                        pNode = GetSibling(pParent);
                        if(pNode != null)
                        {
                            break;  //found it
                        }
                        else
                        {
                            pParent = GetParent(pParent);
                        }
                    }
                }
            }

            return pNode;
        }

        public static Component GetParent(Component pNode)
        {
            Debug.Assert(pNode != null);
            return pNode.pParent;
        }

        public static Component GetChild(Component pNode)
        {
            Debug.Assert(pNode != null);

            Component pChild;
            if(pNode.type == Component.Type.Composite)
            {
                pChild = ((Composite)pNode).GetHead();
            }
            else
            {
                pChild = null;
            }

            return pChild;
        }

        public static Component GetSibling(Component pNode)
        {
            Debug.Assert(pNode != null);
            return (Component)pNode.pNext;
        }

        //-------------------------------------------------------------------
        //  OVERRIDDEN METHODS
        //-------------------------------------------------------------------

        public override Component First()
        {
            Debug.Assert(this.pRoot != null);
            Component pNode = this.pRoot;
            
            this.pCurr = pNode;
            return this.pCurr;
        }

        public override Component Next()
        {
            Debug.Assert(this.pCurr != null);
            Component pNode = this.pCurr;

            Component pChild = GetChild(pNode);
            Component pSibling = GetSibling(pNode);
            Component pParent = GetParent(pNode);

            //depth first: start at root
            pNode = this.NextStep(pNode, pParent, pChild, pSibling);
            this.pCurr = pNode;

            return this.pCurr;
        }

        public override Component Curr()
        {
            return this.pCurr;
        }

        public override bool IsDone()
        {
            return (this.pCurr == null);
        }
    }
}