// Returns possible matches sorted with best-scoring ones first in the list
        private List <BoneMatch> RecursiveFindPotentialBoneMatches(BoneMatch parentMatch, BoneMappingItem goalItem, bool confirmedChoice)
        {
            List <BoneMatch> matches = new List <BoneMatch>();

            // We want to search with breadh first search so we have to use a queue
            Queue <QueuedBone> queue = new Queue <QueuedBone>();

            // Find matches
            queue.Enqueue(new QueuedBone(parentMatch.bone, 0));
            while (queue.Count > 0)
            {
                QueuedBone current = queue.Dequeue();
                Transform  t       = current.bone;
                if (current.level >= goalItem.minStep && (m_TreatDummyBonesAsReal || m_ValidBones == null || (m_ValidBones.ContainsKey(t) && m_ValidBones[t])))
                {
                    BoneMatch match;
                    var       key = GetMatchKey(parentMatch, t, goalItem);
                    if (m_BoneMatchDict.ContainsKey(key))
                    {
                        match = m_BoneMatchDict[key];
                    }
                    else
                    {
                        match = new BoneMatch(parentMatch, t, goalItem);

                        // RECURSIVE CALL
                        EvaluateBoneMatch(match, false);
                        m_BoneMatchDict[key] = match;
                    }

                    if (match.score > 0 || kDebug)
                    {
                        matches.Add(match);
                    }
                }
                SimpleProfiler.Begin("Queue");
                if (current.level < goalItem.maxStep)
                {
                    foreach (Transform child in t)
                    {
                        if (m_ValidBones == null || m_ValidBones.ContainsKey(child))
                        {
                            if (!m_TreatDummyBonesAsReal && m_ValidBones != null && !m_ValidBones[child])
                            {
                                queue.Enqueue(new QueuedBone(child, current.level));
                            }
                            else
                            {
                                queue.Enqueue(new QueuedBone(child, current.level + 1));
                            }
                        }
                    }
                }
                SimpleProfiler.End();
            }

            if (matches.Count == 0)
            {
                return(null);
            }

            // Sort by match score with best matches first
            SimpleProfiler.Begin("SortAndTrim");
            matches.Sort();
            if (matches[0].score <= 0)
            {
                return(null);
            }

            if (kDebug && confirmedChoice)
            {
                DebugMatchChoice(matches);
            }

            // Keep top 3 priorities only for optimization
            while (matches.Count > 3)
            {
                matches.RemoveAt(matches.Count - 1);
            }
            matches.TrimExcess();
            SimpleProfiler.End();

            return(matches);
        }
Exemplo n.º 2
0
        private List <BoneMatch> RecursiveFindPotentialBoneMatches(BoneMatch parentMatch, BoneMappingItem goalItem, bool confirmedChoice)
        {
            List <BoneMatch>   matches = new List <BoneMatch>();
            Queue <QueuedBone> queue   = new Queue <QueuedBone>();

            queue.Enqueue(new QueuedBone(parentMatch.bone, 0));
            while (queue.Count > 0)
            {
                QueuedBone bone = queue.Dequeue();
                Transform  key  = bone.bone;
                if ((bone.level >= goalItem.minStep) && ((this.m_TreatDummyBonesAsReal || (this.m_ValidBones == null)) || (this.m_ValidBones.ContainsKey(key) && this.m_ValidBones[key])))
                {
                    BoneMatch match;
                    int       num = this.GetMatchKey(parentMatch, key, goalItem);
                    if (this.m_BoneMatchDict.ContainsKey(num))
                    {
                        match = this.m_BoneMatchDict[num];
                    }
                    else
                    {
                        match = new BoneMatch(parentMatch, key, goalItem);
                        this.EvaluateBoneMatch(match, false);
                        this.m_BoneMatchDict[num] = match;
                    }
                    if ((match.score > 0f) || kDebug)
                    {
                        matches.Add(match);
                    }
                }
                if (bone.level < goalItem.maxStep)
                {
                    IEnumerator enumerator = key.GetEnumerator();
                    try
                    {
                        while (enumerator.MoveNext())
                        {
                            Transform current = (Transform)enumerator.Current;
                            if ((this.m_ValidBones == null) || this.m_ValidBones.ContainsKey(current))
                            {
                                if ((!this.m_TreatDummyBonesAsReal && (this.m_ValidBones != null)) && !this.m_ValidBones[current])
                                {
                                    queue.Enqueue(new QueuedBone(current, bone.level));
                                }
                                else
                                {
                                    queue.Enqueue(new QueuedBone(current, bone.level + 1));
                                }
                            }
                        }
                    }
                    finally
                    {
                        IDisposable disposable = enumerator as IDisposable;
                        if (disposable != null)
                        {
                            disposable.Dispose();
                        }
                    }
                }
            }
            if (matches.Count == 0)
            {
                return(null);
            }
            matches.Sort();
            if (matches[0].score <= 0f)
            {
                return(null);
            }
            if (kDebug && confirmedChoice)
            {
                this.DebugMatchChoice(matches);
            }
            while (matches.Count > 3)
            {
                matches.RemoveAt(matches.Count - 1);
            }
            matches.TrimExcess();
            return(matches);
        }