void QueueThreadFunction()
        {
            while (QueueRunning)
            {
                QueueEvent.WaitOne();
                bool continueLookup = true;

                while (continueLookup)
                {
                    StateQueueItem item = null;
                    lock (QueueCritSec)
                    {
                        if (Items.Count == 0)
                        {
                            continueLookup = false;
                        }
                        else
                        {
                            item = Items[0];
                            Items.RemoveAt(0);

                            if (item.EventType == StateQueueEventType.CombatListChanged ||
                                item.EventType == StateQueueEventType.CharactersChanged)
                            {
                                Items.RemoveAll(a => a.EventType == item.EventType);
                            }
                            else if (item.EventType == StateQueueEventType.CurrentPlayerChanged)
                            {
                                StateQueueItem lastItem = Items.FindLast(a => a.EventType == StateQueueEventType.CurrentPlayerChanged);

                                if (lastItem != null)
                                {
                                    item = lastItem;
                                }

                                Items.RemoveAll(a => a.EventType == item.EventType);
                            }
                        }
                    }
                    if (item != null)
                    {
                        switch (item.EventType)
                        {
                        case StateQueueEventType.CharactersChanged:
                            callback.CharactersChanged();
                            break;

                        case StateQueueEventType.CombatListChanged:
                            callback.CombatListChanged();
                            break;

                        case StateQueueEventType.CurrentPlayerChanged:
                            callback.CurrentPlayerChanged(item.CharacterID);
                            break;
                        }
                    }
                }
            }
        }
        private void PostToQueue(StateQueueItem item)
        {
            lock (QueueCritSec)
            {
                Items.Add(item);
            }

            QueueEvent.Set();
        }
Example #3
0
        private void ProcessState(StateQueueItem currentState)
        {
            currentState.Page.Scene.Visited = true;

            var states = new HashSet<string>();

            var anchors = Utilities.GetInstance(currentState.Page.Scene.Name, currentState.Page.Scene.LineNumber).ParseAnchors(currentState.Page.Scene.Description).ToList();
            foreach (var action in GetActionsForPage(currentState.Page))
            {
                action.Visited = true;
                anchors.AddRange(Utilities.GetInstance(action.Toggle, action.LineNumber).ParseAnchors(action.Description));
            }
            var conditionals =
                anchors.SelectMany(
                    a => a.Href.Conditions != null ? a.Href.Conditions.Select(c => c.Key) : new string[] {})
                    .Distinct()
                    .ToArray();
            var hasFirstSeen = RegexLib.BlockQuotes.IsMatch(currentState.Page.Scene.Description);

            foreach (var affected in currentState.AffectedStates)
            {
                // signal to previous scenes that this scene's used conditionals are important
                if(currentState.Page.Scene.Conditions != null)
                    foreach (var conditional in currentState.Page.Scene.Conditions)
                        _manager.ToggleStateOn(affected, conditional.Key);
                foreach (var conditional in conditionals) _manager.ToggleStateOn(affected, conditional);

                // signal to previous scenes if this scene has first-seen text
                if (hasFirstSeen) _manager.ToggleSeenSceneOn(affected, currentState.Page.Scene.Id);
            }

            foreach (var anchor in anchors.Where(a => a.Href.Target != null || a.Href.Toggles != null))
            {
                // don't follow links that would be hidden
                if (anchor.Href.Conditions != null &&
                    string.IsNullOrEmpty(
                        Utilities.GetInstance(currentState.Page.Scene.Name, currentState.Page.Scene.LineNumber).ParseConditionalText(anchor.Text)[
                            Utilities.GetInstance(currentState.Page.Scene.Name, currentState.Page.Scene.LineNumber).ConditionsMet(StateResolver.GetStateDictionary(currentState.Page),
                                anchor.Href.Conditions)])) continue;

                var newState = _manager.ResolveNewState(anchor, currentState.Page);
                if (!currentState.Page.Links.ContainsKey(anchor.Original))
                    currentState.Page.Links.Add(anchor.Original, newState.UniqueHash);

                if (!states.Contains(newState.UniqueHash) && !_processed.ContainsKey(newState.UniqueHash))
                {
                    states.Add(newState.UniqueHash);
                    var newAffected = new List<State>(currentState.AffectedStates);
                    newAffected.Add(newState.AffectedState);
                    _processingQueue.Enqueue(new StateQueueItem {Page = newState, AffectedStates = newAffected});
                }
            }
        }
Example #4
0
        private void ProcessState(StateQueueItem currentState)
        {
            currentState.Page.Scene.Visited = true;

            var states = new HashSet <string>();

            var anchors = Utilities.GetInstance(currentState.Page.Scene.Name, currentState.Page.Scene.LineNumber).ParseAnchors(currentState.Page.Scene.Description).ToList();

            foreach (var action in GetActionsForPage(currentState.Page))
            {
                action.Visited = true;
                anchors.AddRange(Utilities.GetInstance(action.Toggle, action.LineNumber).ParseAnchors(action.Description));
            }
            var conditionals =
                anchors.SelectMany(
                    a => a.Href.Conditions != null ? a.Href.Conditions.Select(c => c.Key) : new string[] {})
                .Distinct()
                .ToArray();
            var hasFirstSeen = RegexLib.BlockQuotes.IsMatch(currentState.Page.Scene.Description);

            foreach (var affected in currentState.AffectedStates)
            {
                // signal to previous scenes that this scene's used conditionals are important
                if (currentState.Page.Scene.Conditions != null)
                {
                    foreach (var conditional in currentState.Page.Scene.Conditions)
                    {
                        _manager.ToggleStateOn(affected, conditional.Key);
                    }
                }
                foreach (var conditional in conditionals)
                {
                    _manager.ToggleStateOn(affected, conditional);
                }

                // signal to previous scenes if this scene has first-seen text
                if (hasFirstSeen)
                {
                    _manager.ToggleSeenSceneOn(affected, currentState.Page.Scene.Id);
                }
            }

            foreach (var anchor in anchors.Where(a => a.Href.Target != null || a.Href.Toggles != null))
            {
                // don't follow links that would be hidden
                if (anchor.Href.Conditions != null &&
                    string.IsNullOrEmpty(
                        Utilities.GetInstance(currentState.Page.Scene.Name, currentState.Page.Scene.LineNumber).ParseConditionalText(anchor.Text)[
                            Utilities.GetInstance(currentState.Page.Scene.Name, currentState.Page.Scene.LineNumber).ConditionsMet(StateResolver.GetStateDictionary(currentState.Page),
                                                                                                                                  anchor.Href.Conditions)]))
                {
                    continue;
                }

                var newState = _manager.ResolveNewState(anchor, currentState.Page);
                if (!currentState.Page.Links.ContainsKey(anchor.Original))
                {
                    currentState.Page.Links.Add(anchor.Original, newState.UniqueHash);
                }

                if (!states.Contains(newState.UniqueHash) && !_processed.ContainsKey(newState.UniqueHash))
                {
                    states.Add(newState.UniqueHash);
                    var newAffected = new List <State>(currentState.AffectedStates);
                    newAffected.Add(newState.AffectedState);
                    _processingQueue.Enqueue(new StateQueueItem {
                        Page = newState, AffectedStates = newAffected
                    });
                }
            }
        }