< Summary

Class:DCL.ECSComponents.AnimatorComponentHandler
Assembly:DCL.ECSComponents.Animator
File(s):/tmp/workspace/unity-renderer/unity-renderer/Assets/DCLPlugins/ECS7/ECSComponents/Animator/Handler/AnimatorComponentHandler.cs
Covered lines:30
Uncovered lines:31
Coverable lines:61
Total lines:142
Line coverage:49.1% (30 of 61)
Covered branches:0
Total branches:0

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity NPath complexity Sequence coverage
AnimatorComponentHandler(...)0%110100%
OnComponentCreated(...)0%110100%
OnComponentRemoved(...)0%110100%
OnComponentModelUpdated(...)0%3.13077.78%
ShapeReadyAdded(...)0%2.022083.33%
Initialize(...)0%8.36060%
UpdateAnimationState(...)0%97.6611010.53%
ResetAnimation(...)0%12300%

File(s)

/tmp/workspace/unity-renderer/unity-renderer/Assets/DCLPlugins/ECS7/ECSComponents/Animator/Handler/AnimatorComponentHandler.cs

#LineLine coverage
 1using System;
 2using System.Collections.Generic;
 3using DCL.Components;
 4using DCL.Controllers;
 5using DCL.ECSRuntime;
 6using DCL.Models;
 7using DCL.ECSComponents;
 8using UnityEngine;
 9
 10namespace DCL.ECSComponents
 11{
 12    public class AnimatorComponentHandler : IECSComponentHandler<PBAnimator>
 13    {
 14        private readonly DataStore_ECS7 dataStore;
 15        private IDCLEntity entity;
 16        private PBAnimator model;
 17        internal Animation animComponent;
 18        internal bool isShapeLoaded = false;
 19
 520        internal Dictionary<string, AnimationClip> clipNameToClip = new Dictionary<string, AnimationClip>();
 21
 1522        public AnimatorComponentHandler(DataStore_ECS7 dataStoreEcs7) { dataStore = dataStoreEcs7; }
 23
 524        public void OnComponentCreated(IParcelScene scene, IDCLEntity entity) { }
 25
 26        public void OnComponentRemoved(IParcelScene scene, IDCLEntity entity)
 27        {
 528            dataStore.shapesReady.OnAdded -= ShapeReadyAdded;
 529        }
 30
 31        public void OnComponentModelUpdated(IParcelScene scene, IDCLEntity entity, PBAnimator model)
 32        {
 133            this.entity = entity;
 134            this.model = model;
 35
 36            // If shape is loaded we just update the state of the animation with the model info
 137            if (isShapeLoaded)
 38            {
 039                UpdateAnimationState(model);
 40            }
 41            else
 42            {
 43                // If shape is not loaded, we check if it is already loaded, if not we subscribe to when it is ready
 144                if (dataStore.shapesReady.TryGetValue(entity.entityId, out GameObject gameObject))
 45                {
 046                    ShapeReadyAdded(entity.entityId, gameObject);
 47                }
 48                else
 49                {
 150                    dataStore.shapesReady.OnAdded -= ShapeReadyAdded;
 151                    dataStore.shapesReady.OnAdded += ShapeReadyAdded;
 52                }
 53            }
 154        }
 55
 56        private void ShapeReadyAdded(long entityId, GameObject gameObject)
 57        {
 158            if (entityId != entity.entityId)
 059                return;
 60
 161            Initialize(entity);
 162            isShapeLoaded = true;
 63
 164            UpdateAnimationState(model);
 165        }
 66
 67        internal void Initialize(IDCLEntity entity)
 68        {
 369            if (entity == null)
 070                return;
 71
 72            //NOTE(Brian): fetch all the AnimationClips in Animation component.
 373            animComponent = entity.gameObject.GetComponentInChildren<Animation>(true);
 74
 375            if (animComponent == null)
 076                return;
 77
 378            clipNameToClip.Clear();
 379            int layerIndex = 0;
 80
 381            animComponent.playAutomatically = true;
 382            animComponent.enabled = true;
 383            animComponent.Stop(); //NOTE(Brian): When the GLTF is created by GLTFSceneImporter a frame may be elapsed,
 84            //putting the component in play state if playAutomatically was true at that point.
 385            animComponent.clip?.SampleAnimation(animComponent.gameObject, 0);
 86
 687            foreach (AnimationState unityState in animComponent)
 88            {
 089                clipNameToClip[unityState.clip.name] = unityState.clip;
 90
 091                unityState.clip.wrapMode = WrapMode.Loop;
 092                unityState.layer = layerIndex;
 093                unityState.blendMode = AnimationBlendMode.Blend;
 094                layerIndex++;
 95            }
 396        }
 97
 98        internal void UpdateAnimationState(PBAnimator model)
 99        {
 1100            if (clipNameToClip.Count == 0 || animComponent == null)
 1101                return;
 102
 0103            if (model.States.Count == 0)
 0104                return;
 105
 0106            for (int i = 0; i < model.States.Count; i++)
 107            {
 0108                if (clipNameToClip.ContainsKey(model.States[i].Clip))
 109                {
 0110                    AnimationState unityState = animComponent[model.States[i].Clip];
 0111                    unityState.weight = model.States[i].GetWeight();
 112
 0113                    unityState.wrapMode = model.States[i].GetLoop() ? WrapMode.Loop : WrapMode.Default;
 114
 0115                    unityState.clip.wrapMode = unityState.wrapMode;
 0116                    unityState.speed = model.States[i].GetSpeed();
 0117                    unityState.enabled = model.States[i].Playing;
 118
 0119                    if (model.States[i].ShouldReset)
 0120                        ResetAnimation(model.States[i], unityState.clip);
 121
 0122                    if (model.States[i].Playing && !animComponent.IsPlaying(model.States[i].Clip))
 0123                        animComponent.Play(model.States[i].Clip);
 124                }
 125            }
 0126        }
 127
 128        private void ResetAnimation(PBAnimationState state, AnimationClip clipReference)
 129        {
 0130            if (state == null || clipReference == null)
 131            {
 0132                Debug.LogError("Clip not found");
 0133                return;
 134            }
 135
 0136            animComponent.Stop(state.Clip);
 137
 138            //Manually sample the animation. If the reset is not played again the frame 0 wont be applied
 0139            clipReference.SampleAnimation(animComponent.gameObject, 0);
 0140        }
 141    }
 142}