// Update is called once per frame
        private void populateAnimation(FabulaClip clip)
        {
            // 3 game objects
            agent              = GameObject.Find(clip.gameobject_name);
            location           = GameObject.Find(clip.startingPos_string);
            animTimelineObject = GameObject.Find(clip.animation_string);

            // control track
            control_track_clip             = ctrack.CreateDefaultClip();
            control_track_clip.start       = clip.start + (float)0.12;
            control_track_clip.duration    = clip.duration - (float)0.12;
            control_track_clip.displayName = clip.Name;
            controlAnim = control_track_clip.asset as ControlPlayableAsset;
            AnimateBind(controlAnim, animTimelineObject);

            // nav track
            nav_track_clip             = ntrack.CreateClip <LerpMoveObjectAsset>();
            nav_track_clip.start       = clip.start;
            nav_track_clip.displayName = clip.Name;
            nav_track_clip.duration    = 0.11;
            LerpMoveObjectAsset tp_obj = nav_track_clip.asset as LerpMoveObjectAsset;

            TransformBind(tp_obj, agent, agent.transform, makeCustomizedTransform(location.transform.position, clip.orientation).transform);
            //setClipOffset(animTimelineObject, anim_loc, anim_rot);
        }
示例#2
0
    private void StartPlay(Animator animator, AnimatorStateInfo stateInfo, PlayableDirector director)
    {
        var length          = stateInfo.length;
        var speedMultiplier = stateInfo.speedMultiplier;
        var duration        = TimelineAsset.duration;
        var speed           = duration / (length / speedMultiplier);

        director.playableAsset = TimelineAsset;
        foreach (var outputTrack in TimelineAsset.outputs)
        {
            if (outputTrack.sourceObject is ControlTrack ct)
            {
                foreach (TimelineClip timelineClip in ct.GetClips())
                {
                    ControlPlayableAsset playableAsset = (ControlPlayableAsset)timelineClip.asset;

                    // set the reference of the nested timeline to the parent playable asset
                    director.SetReferenceValue(playableAsset.sourceGameObject.exposedName, animator.gameObject);
                    //// rebind the playableGraph of the parent timeline director
                    //director.RebindPlayableGraphOutputs();
                }
            }
            director.SetGenericBinding(outputTrack.sourceObject, animator.gameObject);
        }
        director.Play();
        director.playableGraph.GetRootPlayable(0).SetSpeed(speed);
    }
示例#3
0
        static bool DetectCycle(ControlPlayableAsset asset, PlayableDirector director, HashSet <PlayableDirector> set)
        {
            if (director == null || asset == null || !asset.updateDirector)
            {
                return(false);
            }

            if (set.Contains(director))
            {
                return(true);
            }

            set.Add(director);
            var gameObject = asset.sourceGameObject.Resolve(director);

            if (gameObject == null)
            {
                return(false);
            }

            foreach (var subDirector in asset.GetComponent <PlayableDirector>(gameObject))
            {
                foreach (var childAsset in GetPlayableAssets(subDirector))
                {
                    if (DetectCycle(childAsset, subDirector, set))
                    {
                        return(true);
                    }
                }
            }
            return(false);
        }
示例#4
0
    private void Update()
    {
        index++;
        if (index > 30)
        {
            var curTime = playable.time;
            foreach (var track in ((TimelineAsset)playable.playableAsset).GetOutputTracks())
            {
                foreach (var clip in track.GetClips())
                {
                    LightControlAsset asset = clip.asset as LightControlAsset;
                    if (asset != null)
                    {
                        playable.SetReferenceValue(asset.light.exposedName, null);
                    }
                }

                // 用修改绑定方法改变
                playable.SetGenericBinding(bindingDict["ActivationTrack"].sourceObject, null);
                if (track as AnimationTrack)
                {
                    playable.SetGenericBinding(track, null);
                }
                else if (track as LightControlTrack)
                {
//                    playable.SetGenericBinding(track, null);
                }

                // 用暂停playableBehaviour方式实现
                var clips = track.GetClips();
                foreach (TimelineClip clip in clips)
                {
                    if (clip.asset as LightControlAsset)
                    {
                        var behaviour = (clip.asset as LightControlAsset).behaviour;
//                        behaviour.OnBehaviourPause();
                    }
                    ControlPlayableAsset asset2 = clip.asset as ControlPlayableAsset;
                    if (asset2 != null)
                    {
                        playable.SetReferenceValue(asset2.sourceGameObject.exposedName, null);
                    }
//                var behaviout = playableAsset.behaviour;
                }
            }
//            playable.RebuildGraph();
            index = -1000000;
        }
    }
示例#5
0
    void ConvertBeatToControlTrack(Beat beat, int index)
    {
        ControlTrack track = TimelineAsset.CreateTrack <ControlTrack>(null, "Collectible_" + index);

        TimelineAsset timelineAsset = CollectiblePrefab.GetComponent <PlayableDirector>().playableAsset as TimelineAsset;

        TimelineClip clip = track.CreateDefaultClip();

        clip.start = beat.BeatStart * (60f / Track.BPM / ((float)Track.TrackSpeed / 4f));

        float beatDuration        = ((beat.BeatEnd - beat.BeatStart) * (60f / Track.BPM / ((float)Track.TrackSpeed / 4f)));
        float collectibleDuration = (float)timelineAsset.duration;

        clip.timeScale = timelineAsset.duration / beatDuration;

        clip.duration = beatDuration;

        ControlPlayableAsset controlPlayableAsset = clip.asset as ControlPlayableAsset;

        controlPlayableAsset.sourceGameObject.exposedName = UnityEditor.GUID.Generate().ToString();
        switch (beat.BeatLocation)
        {
        case BeatLocation.Center:
            PlayableDirector.SetReferenceValue(controlPlayableAsset.sourceGameObject.exposedName, CenterZone);
            break;

        case BeatLocation.North:
            PlayableDirector.SetReferenceValue(controlPlayableAsset.sourceGameObject.exposedName, NorthZone);
            break;

        case BeatLocation.South:
            PlayableDirector.SetReferenceValue(controlPlayableAsset.sourceGameObject.exposedName, SouthZone);
            break;

        case BeatLocation.East:
            PlayableDirector.SetReferenceValue(controlPlayableAsset.sourceGameObject.exposedName, EastZone);
            break;

        case BeatLocation.West:
            PlayableDirector.SetReferenceValue(controlPlayableAsset.sourceGameObject.exposedName, WestZone);
            break;
        }

        controlPlayableAsset.prefabGameObject   = CollectiblePrefab;
        controlPlayableAsset.updateParticle     = false;
        controlPlayableAsset.updateITimeControl = false;
        controlPlayableAsset.updateDirector     = true;
    }
    public void StartTimelineInstance()
    {
        // instantiate the nested timeline
        m_generatedNestedTimelineObject = Instantiate(m_nestedCassetteTimeline, transform);
        var nestedTimeline = m_generatedNestedTimelineObject.GetComponent <PlayableDirector>();

        nestedTimeline.stopped += (director) =>
        {
            // when the nested timeline finished playing, the parent is allowed to move forward the set marker
            timelineConditionMet = true;
            Destroy(m_generatedNestedTimelineObject);
        };

        // create parent timeline bindings
        foreach (var track in m_timelineDirector.playableAsset.outputs)
        {
            if (track.sourceObject is ControlTrack)
            {
                ControlTrack ct = (ControlTrack)track.sourceObject;
                if (ct.name == "nestedTimeline")
                {
                    foreach (TimelineClip timelineClip in ct.GetClips())
                    {
                        ControlPlayableAsset playableAsset = (ControlPlayableAsset)timelineClip.asset;
                        playableAsset.postPlayback   = ActivationControlPlayable.PostPlaybackState.Revert;
                        playableAsset.updateDirector = false;
                        playableAsset.updateParticle = false;

                        // set the reference of the nested timeline to the parent playable asset
                        m_timelineDirector.SetReferenceValue(playableAsset.sourceGameObject.exposedName, nestedTimeline.gameObject);
                        // rebind the playableGraph of the parent timeline director
                        m_timelineDirector.RebindPlayableGraphOutputs();
                    }
                }
            }
        }

        // now I can play the timeline
        m_timelineDirector.Play();
    }
示例#7
0
    // Start is called before the first frame update
    void Start()
    {
        playable    = gameObject.GetComponent <PlayableDirector>();
        light       = gameObject.GetComponent <Light>();
        bindingDict = new Dictionary <string, PlayableBinding>();
        foreach (var bind in playable.playableAsset.outputs)
        {
            bindingDict.Add(bind.streamName, bind);
        }

        // 动态绑定轨道中的节点 SetGenericBinding
//        playable.SetGenericBinding(bindingDict["LightTrack1"].sourceObject, light);
        playable.SetGenericBinding(bindingDict["Animation1"].sourceObject, sphere);


        // 动态绑定轨道中clip的节点 SetReferenceValue
        foreach (var track in ((TimelineAsset)playable.playableAsset).GetOutputTracks())
        {
//            track.muted = false;
            foreach (var clip in track.GetClips())
            {
                LightControlAsset asset = clip.asset as LightControlAsset;
                if (asset != null)
                {
                    playable.SetReferenceValue(asset.light.exposedName, light);
                }
                ControlPlayableAsset asset2 = clip.asset as ControlPlayableAsset;
                if (asset2 != null)
                {
                    playable.SetReferenceValue(asset2.sourceGameObject.exposedName, sphere);
                }
            }
        }
        playable.SetGenericBinding(bindingDict["ActivationTrack"].sourceObject, null);
//        playable.RebuildGraph();
        // 获取track信息
        TimelineAsset timelineAsset = (TimelineAsset)playable.playableAsset;
//        timelineAsset.DeleteTrack()
//        timelineAsset.A
        var count = timelineAsset.outputTrackCount;

        for (int i = 1; i < count; i++)
        {
            TrackAsset asset = timelineAsset.GetOutputTrack(i);
            var        clips = asset.GetClips();
            foreach (TimelineClip clip in clips)
            {
                var playableAsset = (PlayableAsset)clip.asset;
                var lightAsset    = playableAsset as LightControlAsset;
                if (lightAsset != null)
                {
//                    lightAsset.behaviour.OnGraphStop();
                }
//                var behaviout = playableAsset.behaviour;
            }
        }

//        var graphCount = playable.playableGraph.GetOutputCount();
//        for (int i = 0; i < graphCount; i++)
//        {
//
////            var playable1 = playable.playableGraph.GetRootPlayable(i);
//            PlayableOutput output = playable.playableGraph.GetOutput(i);
//            var p1 = output.GetSourcePlayable();
////            p1.GetInputCount();
//            Playable i1 = p1.GetInput(1);
////            playable.playableAsset
////            i1.SetInputWeight(0);
//
////            output.SetWeight();
//            var graph = playable.playableGraph;
////            graph
//            var playable2 = output.GetSourcePlayable();
//        }
        playable.Play();
    }
示例#8
0
 public static void ControlTrackSetGameObject(PlayableDirector director, ControlPlayableAsset clip, GameObject obj)
 {
     director.playableGraph.GetResolver().SetReferenceValue(clip.sourceGameObject.exposedName, obj);
 }
 public void AnimateBind(ControlPlayableAsset cpa, GameObject ato)
 {
     cpa.sourceGameObject.exposedName = UnityEditor.GUID.Generate().ToString();
     playableDirector.SetReferenceValue(cpa.sourceGameObject.exposedName, ato);
 }
示例#10
0
    public void BuildTimeline()
    {
        Debug.Log("Buidilng Timeline");
        TimelineAsset timelineAsset = (TimelineAsset)timeline.playableAsset;

        //TODO: make it so that it deletes all tracks and rebuilds them every each time
        for (int i = 0; i < timelineAsset.rootTrackCount; i++)
        {
            timelineAsset.DeleteTrack(timelineAsset.GetRootTrack(0));
        }
        for (int i = 0; i < timelineAsset.outputTrackCount; i++)
        {
            timelineAsset.DeleteTrack(timelineAsset.GetOutputTrack(0));
        }

        ControlTrack controlTrack = (ControlTrack)timelineAsset.CreateTrack(typeof(ControlTrack), null, "Control Track");

        clipToTime = new Dictionary <ClipSettings, double>();

        // map all timeline clips first
        for (int i = 0; i < timelineClips.Count; i++)
        {
            TimelineClip         tc  = controlTrack.CreateDefaultClip();
            ControlPlayableAsset cpa = tc.asset as ControlPlayableAsset;
            cpa.sourceGameObject.exposedName = UnityEditor.GUID.Generate().ToString();
            timeline.SetReferenceValue(cpa.sourceGameObject.exposedName, timelineClips[i].timelineTrack.gameObject);

            if (i != 0)
            {
                tc.start = tc.start + 1;
            }

            clipToTime.Add(timelineClips[i], tc.start);

            tc.duration = timelineClips[i].timelineTrack.duration;
        }

        //map remix clips
        int j = 0;

        foreach (TimelineClip tc in controlTrack.GetClips())
        {
            foreach (TriggerMapping triggerMapping in timelineClips[j].triggers)
            {
                TimeMachineTrack timeMachineTrack = (TimeMachineTrack)timelineAsset.CreateTrack(typeof(TimeMachineTrack), null, "Trigger Track");
                if (triggerMapping.type == TriggerType.CONTINUOUS)
                {
                    TimelineClip     triggerCip = timeMachineTrack.CreateDefaultClip();
                    TimeMachineAsset tma        = triggerCip.asset as TimeMachineAsset;

                    tma.action          = TimeMachineBehavior.TimeMachineAction.JumpToTime;
                    tma.condition       = TimeMachineBehavior.Condition.TriggerOff;
                    tma.timeToJumpTo    = (float)clipToTime[triggerMapping.targetTrack];
                    triggerCip.start    = tc.start;
                    triggerCip.duration = tc.duration;


                    tma.trigger.exposedName = UnityEditor.GUID.Generate().ToString();
                    // tma.timeToJumpTo = triggerMapping.timeToJumpTo;
                    timeline.SetReferenceValue(tma.trigger.exposedName, triggerMapping.trigger);
                }
                else
                {
                    TimelineClip     triggerCip = timeMachineTrack.CreateDefaultClip();
                    TimeMachineAsset tma        = triggerCip.asset as TimeMachineAsset;

                    tma.action          = TimeMachineBehavior.TimeMachineAction.JumpToTime;
                    tma.condition       = TimeMachineBehavior.Condition.TriggerOff;
                    tma.timeToJumpTo    = (float)clipToTime[triggerMapping.targetTrack];
                    triggerCip.start    = tc.end;
                    triggerCip.duration = 1;

                    tma.trigger.exposedName = UnityEditor.GUID.Generate().ToString();
                    timeline.SetReferenceValue(tma.trigger.exposedName, triggerMapping.trigger);
                }
            }
            j++;
        }
        Debug.Log("Finished");
    }
示例#11
0
    public override void ExecuteState(StateMachine stateMachine, IState prevState, object param1, object param2)
    {
        base.ExecuteState(stateMachine, prevState, param1, param2);

        mCurrSkillID = (int)param1;
        mChangeState = false;

        mSkillInfo = SkillConfig.singleton.GetSkillInfo(mCurrSkillID);
        if (mSkillInfo == null || mSkillInfo.mTimeline == null)
        {
            return;
        }
        mTargetRole = mRole.mRoleData.GetTargetRole();

        if (Skill.ExecuteSkill(mRole, mTargetRole, mSkillInfo))
        {
            mChangeState = false;
        }
        else
        {
            StateComplete();
            return;
        }

        // 获取timeline
        mDirector = mSkillInfo.mTimeline.GetComponent <PlayableDirector>();
        mDirector.Stop();

        // 取出timeline 左边的名字进行绑定右边的资源
        foreach (PlayableBinding bind in mDirector.playableAsset.outputs)
        {
            if (bind.streamName == "Self")
            {
                AnimationTrack animationTrack = bind.sourceObject as AnimationTrack;
                mDuringTime = (float)animationTrack.duration;
                mBeginTime  = Time.fixedTime;
                mDirector.SetGenericBinding(bind.sourceObject, mAnimator);
            }
            else if (bind.streamName == "Target")
            {
                mDirector.SetGenericBinding(bind.sourceObject, mTargetRole.mAnimator);

                mRole.transform.position = -mRole.transform.forward * mSkillInfo.mAtkDistance + mTargetRole.transform.position;

                mRole.mRoleData.SetForward(mTargetRole.transform.position, mRole.transform.position);
                mRole.transform.rotation = Quaternion.LookRotation(mRole.mRoleData.GetForward());

                mTargetRole.mRoleData.SetForward(mRole.transform.position, mTargetRole.transform.position);
                mTargetRole.transform.rotation = Quaternion.LookRotation(mTargetRole.mRoleData.GetForward());
            }
            else if (bind.streamName == "SelfEffect")
            {
                mDirector.SetGenericBinding(bind.sourceObject, mSkillInfo.mSelfEffect);
            }
            else if (bind.streamName == "TargetEffect")
            {
                mDirector.SetGenericBinding(bind.sourceObject, mSkillInfo.mTargetEffect);
            }
            else if (bind.streamName == "Control Track")
            {
                ControlTrack ct = bind.sourceObject as ControlTrack;
                foreach (var clip in ct.GetClips())
                {
                    ControlPlayableAsset playableAsset = clip.asset as ControlPlayableAsset;
                    mDirector.SetReferenceValue(playableAsset.sourceGameObject.exposedName, mRole.gameObject);
                }
            }
            else if (bind.streamName == "Playable Track")
            {
                PlayableTrack ct = bind.sourceObject as PlayableTrack;
                foreach (TimelineClip clip in ct.GetClips())
                {
                    PlayableAssetEx playableAsset = clip.asset as PlayableAssetEx;
                    if (playableAsset)
                    {
                        // 1.自定义脚本获取绑定 自定义的变量
                        playableAsset.mParamAttackTL = this;
                    }
                }
            }
        }

        mDirector.Play(); // 播放timeline
    }
        private void populateNavigation(FabulaClip clip)
        {
            agent             = GameObject.Find(clip.gameobject_name);
            starting_location = GameObject.Find(clip.startingPos_string);
            location          = GameObject.Find(clip.endingPos_string);
            var animTimelineObject_template = GameObject.Find(clip.animation_string);

            animTimelineObject = Instantiate(animTimelineObject_template);
            var director01 = animTimelineObject.GetComponent <PlayableDirector>();
            var timeline   = director01.playableAsset as TimelineAsset;

            foreach (var track in timeline.GetOutputTracks())
            {
                var animTrack = track as AnimationTrack;
                if (animTrack == null)
                {
                    continue;
                }
                var binding = director01.GetGenericBinding(animTrack);
                if (binding == null)
                {
                    continue;
                }

                // the binding can be an animator or game object with an animator
                //var animator = binding as Animator;
                //var gameobject_original = binding as GameObject;
                //var animator01 = gameObject.GetComponent<Animator>();

                director01.SetGenericBinding(animTrack, agent.GetComponent <Animator>());
            }

            // get vector3 corresponding to destination - origin
            Vector3 dest_minus_origin = location.transform.position - starting_location.transform.position;
            float   orientation       = Mathf.Atan2(dest_minus_origin.x, -dest_minus_origin.z) * Mathf.Rad2Deg - 90f;
            //float orientation = Mathf.Atan2(location.transform.position.z, -location.transform.position.x) * Mathf.Rad2Deg;

            //nav_track_clip = ntrack.CreateClip<LerpMoveObjectAsset1>();
            //nav_track_clip.start = clip.start;
            //nav_track_clip.displayName = clip.Name + "_transport";
            //nav_track_clip.duration = 0.11;
            //LerpMoveObjectAsset1 tp_obj = nav_track_clip.asset as LerpMoveObjectAsset1;
            Transform start_transform = makeCustomizedTransform(starting_location.transform.position, orientation).transform;

            //TransformBind1(tp_obj, agent, start_transform);

            nav_track_clip2 = ntrack.CreateClip <LerpMoveObjectAsset>();
            //nav_track_clip2.start = clip.start + (float)0.12;
            //nav_track_clip2.duration = clip.duration - (float)0.12;
            nav_track_clip2.start    = clip.start;
            nav_track_clip2.duration = clip.duration;
            LerpMoveObjectAsset lerp_clip     = nav_track_clip2.asset as LerpMoveObjectAsset;
            Transform           end_transform = makeCustomizedTransform(location.transform.position, orientation).transform;

            TransformBind(lerp_clip, agent, start_transform, end_transform);

            // control track - animate
            control_track_clip             = ctrack.CreateDefaultClip();
            control_track_clip.start       = clip.start + (float)0.12;
            control_track_clip.duration    = clip.duration - (float)0.12;
            control_track_clip.displayName = clip.Name;
            controlAnim = control_track_clip.asset as ControlPlayableAsset;
            AnimateBind(controlAnim, animTimelineObject);

            //FabulaAction FA = new FabulaAction();
            //FA.start = (float)control_track_clip.start;
            //FA.duration = (float)control_track_clip.duration;
            //FA.NavObj = agent;
            //FA.end_pos = end_transform.position;
            //FA.start_pos = start_transform.position;
            //FA.orientation = orientation;
            //navDict.Add(clip.Name, FA);
        }
示例#13
0
    static void ParseScreenplay()
    {
        Clear();

        // load file
        var      selectedFilepath = EditorUtility.OpenFilePanel("Select Screenplay", "", "txt");
        FileInfo fileInfo         = new FileInfo(selectedFilepath);
        string   timeText         = System.DateTime.Now.ToString("hh.mm.ss"); // get time so we can mark where these changes were made

        // create playabledirector in scene
        currentPlayableGameObject = new GameObject();

        currentPlayableGameObject.name = fileInfo.Name.Replace(".txt", string.Empty) + " " + timeText + " Timeline";
        currentDataSlate = currentPlayableGameObject.AddComponent <screenwriterDataSlate> ();
        currentPlayable  = currentPlayableGameObject.AddComponent <PlayableDirector> ();

        // create timeline asset
        TimelineAsset currentTimeline = ScriptableObject.CreateInstance("TimelineAsset") as TimelineAsset;

        AssetDatabase.CreateAsset(currentTimeline, "Assets/Timelines/" + fileInfo.Name.Replace(".txt", string.Empty) + " " + timeText + ".playable");

        currentTimeline = (TimelineAsset)AssetDatabase.LoadAssetAtPath("Assets/Timelines/" + fileInfo.Name.Replace(".txt", string.Empty) + " " + timeText + ".playable", typeof(TimelineAsset));

        currentPlayable.playableAsset = currentTimeline;

        masterTrack = currentTimeline.CreateTrack <GroupTrack> (null, "Master Group");
        currentTimeline.CreateTrack <ControlTrack> (masterTrack, "Shots");
        currentTimeline.CreateTrack <ControlTrack> (masterTrack, "Lighting");
        //      currentTimeline.CreateTrack<SignalTrack> (null, "Track");
        //      currentTimeline.CreateTrack<AnimationTrack> (null, "Track");

        string filePath = fileInfo.FullName;

        line = null;
        StreamReader reader = new StreamReader(filePath);

        using (reader) {
            do
            {
                thirdLastLine = lastLine;
                lastLine      = line;
                line          = reader.ReadLine();
                if (System.String.IsNullOrEmpty(line) == false)
                {
                    // this is where we actually parse the screenplay

                    lineCount++;
                    //  print ("Parsing line #" + lineCount);

                    // capital letters checker
                    char[] possibleCharacter = line.ToCharArray();
                    int    capitalization    = 0;
                    for (int i = 0; i < possibleCharacter.Length; i++)
                    {
                        if (System.Char.IsUpper(possibleCharacter[i]))
                        {
                            capitalization++;
                        }
                    }

                    // location, time of day
                    if (line.Contains("EXT") || line.Contains("INT"))
                    {
                        char splitChar = '-';

                        string[] splitString = line.Split(splitChar);

                        currentDataSlate.TryAddLocation(splitString[0]);
                        currentLocation = splitString[0];

                        currentDataSlate.TryAddLightingScenario(splitString[1]);
                        currentLightingScenario = splitString[1];
                        continue;
                    }

                    // character check - all capitals and no :
                    if (capitalization > possibleCharacter.Length * 0.8f && line.Contains(":") == false)
                    {
                        currentDataSlate.TryAddCharacter(line);
                        currentCharacter = line;
                        continue;
                    }

                    // extra actor instructions check - has ()
                    if (line.Contains("("))
                    {
                        currentMood = line;
                        continue;
                    }

                    // transition data - contains : and is caps
                    if (line.Contains(":") && capitalization > possibleCharacter.Length * 0.5f)
                    {
                        continue;
                    }

                    // at this point there arent many edge cases left - check if we have a actor guidelines or an actor name above us to see if this is dialogue
                    if (lastLine != null)
                    {
                        if (lastLine.Contains("(") || currentDataSlate.characters.Contains(lastLine))
                        {
                            //dialogue callback

                            // check if we already have a character group
                            bool alreadyCreatedCharacter = false;
                            IEnumerable <TrackAsset> duplicateCharacterCheck = currentTimeline.GetRootTracks();
                            foreach (TrackAsset track in duplicateCharacterCheck)
                            {
                                print(track.name);
                                if (track.name == currentCharacter)
                                {
                                    alreadyCreatedCharacter = true;
                                }
                            }

                            if (alreadyCreatedCharacter == false)
                            {
                                TrackAsset characterTrack      = currentTimeline.CreateTrack <GroupTrack> (null, currentCharacter);
                                TrackAsset possibleSignalTrack = currentTimeline.CreateTrack <SignalTrack> (characterTrack, currentCharacter + " Signals");
                                TrackAsset animationTrack      = currentTimeline.CreateTrack <AnimationTrack> (characterTrack, currentCharacter + " Animation Overrides");
                            }

                            IEnumerable <TrackAsset> allTracksForActors = currentTimeline.GetOutputTracks();
                            foreach (TrackAsset track in allTracksForActors)
                            {
                                if (track.name == currentCharacter + " Signals")
                                {
                                    IMarker newMarker = track.CreateMarker <SignalEmitter> (currentTimelineScrub);
                                }
                                if (track.name == currentCharacter + " Animation Overrides")
                                {
                                    TimelineClip newClip = track.CreateDefaultClip();
                                    newClip.start       = currentTimelineScrub;
                                    newClip.duration    = Convert.ToDouble(line.Length) / 12.0;
                                    newClip.displayName = "Dialogue Animation";
                                }
                            }
                        }
                    }

                    // shot callback
                    IEnumerable <TrackAsset> allTracksForActions = currentTimeline.GetOutputTracks();
                    foreach (TrackAsset track in allTracksForActions)
                    {
                        if (track.name == "Shots")
                        {
                            GameObject cameraInstance = PrefabUtility.InstantiatePrefab(currentDataSlate.cameraPrefab) as GameObject;
                            cameraInstance.name             = "Shot Camera";
                            cameraInstance.transform.parent = currentPlayableGameObject.transform;

                            //   TimelineClip newClip = track.CreateDefaultClip ();
                            //

                            TimelineClip         tlClip = track.CreateClip <ControlPlayableAsset> ();
                            ControlPlayableAsset clip   = tlClip.asset as ControlPlayableAsset;
                            clip.sourceGameObject.exposedName = UnityEditor.GUID.Generate().ToString();
                            currentPlayable.SetReferenceValue(clip.sourceGameObject.exposedName, cameraInstance);

                            tlClip.clipIn      = currentTimelineScrub;
                            tlClip.duration    = Convert.ToDouble(line.Length) / 12.0;
                            tlClip.displayName = line;
                        }
                        if (track.name == "Lighting")
                        {
                            TimelineClip newClip = track.CreateDefaultClip();
                            newClip.displayName = currentLightingScenario;
                            newClip.clipIn      = currentTimelineScrub;
                            newClip.duration    = Convert.ToDouble(line.Length) / 12.0;
                        }
                    }

                    currentTimelineScrub = currentTimeline.duration;
                }
            }while (line != null);
            reader.Close();
        }
    }