Inheritance: Parsed.Object
Example #1
0
        public Sequence(List <ContentList> elementContentLists, SequenceType sequenceType)
        {
            this.sequenceType     = sequenceType;
            this.sequenceElements = new List <Parsed.Object> ();

            foreach (var elementContentList in elementContentLists)
            {
                var contentObjs = elementContentList.content;

                Parsed.Object seqElObject = null;

                // Don't attempt to create a weave for the sequence element
                // if the content list is empty. Weaves don't like it!
                if (contentObjs == null || contentObjs.Count == 0)
                {
                    seqElObject = elementContentList;
                }
                else
                {
                    seqElObject = new Weave(contentObjs);
                }

                this.sequenceElements.Add(seqElObject);
                AddContent(seqElObject);
            }
        }
Example #2
0
        List<Parsed.Object> SplitWeaveAndSubFlowContent(List<Parsed.Object> contentObjs)
        {
            var weaveObjs = new List<Parsed.Object> ();
            var subFlowObjs = new List<Parsed.Object> ();

            _subFlowsByName = new Dictionary<string, FlowBase> ();

            foreach (var obj in contentObjs) {

                var subFlow = obj as FlowBase;
                if (subFlow) {
                    if (_firstChildFlow == null)
                        _firstChildFlow = subFlow;

                    subFlowObjs.Add (obj);
                    _subFlowsByName [subFlow.name] = subFlow;
                } else {
                    weaveObjs.Add (obj);
                }
            }

            var finalContent = new List<Parsed.Object> ();
            if (weaveObjs.Count > 0) {
                _rootWeave = new Weave (weaveObjs, 0);
                finalContent.Add (_rootWeave);
            }
            if (subFlowObjs.Count > 0) {
                finalContent.AddRange (subFlowObjs);
            }

            return finalContent;
        }
Example #3
0
        List <Parsed.Object> SplitWeaveAndSubFlowContent(List <Parsed.Object> contentObjs)
        {
            var weaveObjs   = new List <Parsed.Object> ();
            var subFlowObjs = new List <Parsed.Object> ();

            _subFlowsByName = new Dictionary <string, FlowBase> ();

            foreach (var obj in contentObjs)
            {
                var subFlow = obj as FlowBase;
                if (subFlow)
                {
                    subFlowObjs.Add(obj);
                    _subFlowsByName [subFlow.name] = subFlow;
                }
                else
                {
                    weaveObjs.Add(obj);
                }
            }

            var finalContent = new List <Parsed.Object> ();

            if (weaveObjs.Count > 0)
            {
                _rootWeave = new Weave(weaveObjs, 0);
                finalContent.Add(_rootWeave);
            }
            if (subFlowObjs.Count > 0)
            {
                finalContent.AddRange(subFlowObjs);
            }

            return(finalContent);
        }
Example #4
0
 public ConditionalSingleBranch(List<Parsed.Object> content)
 {
     // Branches are allowed to be empty
     if (content != null) {
         _innerWeave = new Weave (content);
         AddContent (_innerWeave);
     }
 }
 public ConditionalSingleBranch(List <Parsed.Object> content)
 {
     // Branches are allowed to be empty
     if (content != null)
     {
         _innerWeave = new Weave(content);
         AddContent(_innerWeave);
     }
 }
Example #6
0
        void ConstructWeaveHierarchyFromIndentation()
        {
            // Find nested indentation and convert to a proper object hierarchy
            // (i.e. indented content is replaced with a Weave object that contains
            // that nested content)
            int contentIdx = 0;

            while (contentIdx < content.Count)
            {
                Parsed.Object obj = content [contentIdx];

                // Choice or Gather
                if (obj is IWeavePoint)
                {
                    var weavePoint     = (IWeavePoint)obj;
                    var weaveIndentIdx = weavePoint.indentationDepth - 1;

                    // Inner level indentation - recurse
                    if (weaveIndentIdx > baseIndentIndex)
                    {
                        // Step through content until indent jumps out again
                        int innerWeaveStartIdx = contentIdx;
                        while (contentIdx < content.Count)
                        {
                            var innerWeaveObj = content [contentIdx] as IWeavePoint;
                            if (innerWeaveObj != null)
                            {
                                var innerIndentIdx = innerWeaveObj.indentationDepth - 1;
                                if (innerIndentIdx <= baseIndentIndex)
                                {
                                    break;
                                }
                            }

                            contentIdx++;
                        }

                        int weaveContentCount = contentIdx - innerWeaveStartIdx;

                        var weaveContent = content.GetRange(innerWeaveStartIdx, weaveContentCount);
                        content.RemoveRange(innerWeaveStartIdx, weaveContentCount);

                        var weave = new Weave(weaveContent, weaveIndentIdx);
                        InsertContent(innerWeaveStartIdx, weave);

                        // Continue iteration from this point
                        contentIdx = innerWeaveStartIdx;
                    }
                }

                contentIdx++;
            }
        }
Example #7
0
        // Add nested block at a greater indentation level
        public void AddRuntimeForNestedWeave(Weave nestedResult)
        {
            // Add this inner block to current container
            // (i.e. within the main container, or within the last defined Choice/Gather)
            AddGeneralRuntimeContent(nestedResult.rootContainer);

            // Now there's a deeper indentation level, the previous weave point doesn't
            // count as a loose end (since it will have content to go to)
            if (previousWeavePoint != null)
            {
                looseEnds.Remove(previousWeavePoint);
                addContentToPreviousWeavePoint = false;
            }
        }
Example #8
0
        List <Parsed.Object> SplitWeaveAndSubFlowContent(List <Parsed.Object> contentObjs, bool isRootStory)
        {
            var weaveObjs   = new List <Parsed.Object> ();
            var subFlowObjs = new List <Parsed.Object> ();

            _subFlowsByName = new Dictionary <string, FlowBase> ();

            foreach (var obj in contentObjs)
            {
                var subFlow = obj as FlowBase;
                if (subFlow)
                {
                    if (_firstChildFlow == null)
                    {
                        _firstChildFlow = subFlow;
                    }

                    subFlowObjs.Add(obj);
                    _subFlowsByName [subFlow.identifier?.name] = subFlow;
                }
                else
                {
                    weaveObjs.Add(obj);
                }
            }

            // Implicit final gather in top level story for ending without warning that you run out of content
            if (isRootStory)
            {
                weaveObjs.Add(new Gather(null, 1));
                weaveObjs.Add(new Divert(new Path(Identifier.Done)));
            }

            var finalContent = new List <Parsed.Object> ();

            if (weaveObjs.Count > 0)
            {
                _rootWeave = new Weave(weaveObjs, 0);
                finalContent.Add(_rootWeave);
            }

            if (subFlowObjs.Count > 0)
            {
                finalContent.AddRange(subFlowObjs);
            }

            return(finalContent);
        }
Example #9
0
        void PassLooseEndsToAncestors()
        {
            if (looseEnds.Count == 0)
            {
                return;
            }

            // Search for Weave ancestor to pass loose ends to for gathering.
            // There are two types depending on whether the current weave
            // is separated by a conditional or sequence.
            //  - An "inner" weave is one that is directly connected to the current
            //    weave - i.e. you don't have to pass through a conditional or
            //    sequence to get to it. We're allowed to pass all loose ends to
            //    one of these.
            //  - An "outer" weave is one that is outside of a conditional/sequence
            //    that the current weave is nested within. We're only allowed to
            //    pass gathers (i.e. 'normal flow') loose ends up there, not normal
            //    choices. The rule is that choices have to be diverted explicitly
            //    by the author since it's ambiguous where flow should go otherwise.
            //
            // e.g.:
            //
            //   - top                       <- e.g. outer weave
            //   {true:
            //       * choice                <- e.g. inner weave
            //         * * choice 2
            //             more content      <- e.g. current weave
            //       * choice 2
            //   }
            //   - more of outer weave
            //
            Weave closestInnerWeaveAncestor = null;
            Weave closestOuterWeaveAncestor = null;

            // Find inner and outer ancestor weaves as defined above.
            bool nested = false;

            for (var ancestor = this.parent; ancestor != null; ancestor = ancestor.parent)
            {
                // Found ancestor?
                var weaveAncestor = ancestor as Weave;
                if (weaveAncestor != null)
                {
                    if (!nested && closestInnerWeaveAncestor == null)
                    {
                        closestInnerWeaveAncestor = weaveAncestor;
                    }

                    if (nested && closestOuterWeaveAncestor == null)
                    {
                        closestOuterWeaveAncestor = weaveAncestor;
                    }
                }


                // Weaves nested within Sequences or Conditionals are
                // "sealed" - any loose ends require explicit diverts.
                if (ancestor is Sequence || ancestor is Conditional)
                {
                    nested = true;
                }
            }

            // No weave to pass loose ends to at all?
            if (closestInnerWeaveAncestor == null && closestOuterWeaveAncestor == null)
            {
                return;
            }

            // Follow loose end passing logic as defined above
            for (int i = looseEnds.Count - 1; i >= 0; i--)
            {
                var looseEnd = looseEnds[i];

                bool received = false;

                // This weave is nested within a conditional or sequence:
                //  - choices can only be passed up to direct ancestor ("inner") weaves
                //  - gathers can be passed up to either, but favour the closer (inner) weave
                //    if there is one
                if (nested)
                {
                    if (looseEnd is Choice && closestInnerWeaveAncestor != null)
                    {
                        closestInnerWeaveAncestor.ReceiveLooseEnd(looseEnd);
                        received = true;
                    }

                    else if (!(looseEnd is Choice))
                    {
                        var receivingWeave = closestInnerWeaveAncestor ?? closestOuterWeaveAncestor;
                        if (receivingWeave != null)
                        {
                            receivingWeave.ReceiveLooseEnd(looseEnd);
                            received = true;
                        }
                    }
                }

                // No nesting, all loose ends can be safely passed up
                else
                {
                    closestInnerWeaveAncestor.ReceiveLooseEnd(looseEnd);
                    received = true;
                }

                if (received)
                {
                    looseEnds.RemoveAt(i);
                }
            }
        }
Example #10
0
File: Weave.cs Project: tomkail/ink
        void ConstructWeaveHierarchyFromIndentation()
        {
            // Find nested indentation and convert to a proper object hierarchy
            // (i.e. indented content is replaced with a Weave object that contains
            // that nested content)
            int contentIdx = 0;
            while (contentIdx < content.Count) {

                Parsed.Object obj = content [contentIdx];

                // Choice or Gather
                if (obj is IWeavePoint) {
                    var weavePoint = (IWeavePoint)obj;
                    var weaveIndentIdx = weavePoint.indentationDepth - 1;

                    // Inner level indentation - recurse
                    if (weaveIndentIdx > baseIndentIndex) {

                        // Step through content until indent jumps out again
                        int innerWeaveStartIdx = contentIdx;
                        while (contentIdx < content.Count) {
                            var innerWeaveObj = content [contentIdx] as IWeavePoint;
                            if (innerWeaveObj != null) {
                                var innerIndentIdx = innerWeaveObj.indentationDepth - 1;
                                if (innerIndentIdx <= baseIndentIndex) {
                                    break;
                                }
                            }

                            contentIdx++;
                        }

                        int weaveContentCount = contentIdx - innerWeaveStartIdx;

                        var weaveContent = content.GetRange (innerWeaveStartIdx, weaveContentCount);
                        content.RemoveRange (innerWeaveStartIdx, weaveContentCount);

                        var weave = new Weave (weaveContent, weaveIndentIdx);
                        InsertContent (innerWeaveStartIdx, weave);

                        // Continue iteration from this point
                        contentIdx = innerWeaveStartIdx;
                    }

                }

                contentIdx++;
            }
        }
Example #11
0
File: Weave.cs Project: tomkail/ink
        // Add nested block at a greater indentation level
        public void AddRuntimeForNestedWeave(Weave nestedResult)
        {
            // Add this inner block to current container
            // (i.e. within the main container, or within the last defined Choice/Gather)
            AddGeneralRuntimeContent (nestedResult.rootContainer);

            // Now there's a deeper indentation level, the previous weave point doesn't
            // count as a loose end (since it will have content to go to)
            if (previousWeavePoint != null) {
                looseEnds.Remove ((Parsed.Object)previousWeavePoint);
                addContentToPreviousWeavePoint = false;
            }
        }