Switching camera's opun PlayerDied

I tried setting up another camera to see if I understand now how to do it, but I think I’m missing something still.

I created a new state in the Animator called ‘PlayerDied’.

Then I went into the StateDrivenCaerma in the inspector and added a State PlayerDied and set the Camera to the DiedCamera that I put within the StateDriverCamera object in the Hierarchy.

Then in my PlayerDeadState I added these lines:

private readonly int DiedHash = Animator.StringToHash("PlayerDied");
private const float CrossFadeDuration = 0.12f;

and in the Enter method I added

stateMachine.Animator.CrossFadeInFixedTime(DiedHash, CrossFadeDuration);

buttt… It’s not working. What am I missing here? Thanks a bunch!

That sounds very much like the right steps.

Paste in a screenshot of your Animator, and a Screenshot of your StateDrivenCamera Heirarchy and settings.

And I set the DiedCamera to close up on his face

The weird thing is that when I start the game now, the angle at which the camera starts, is in front of the player, just like my diedCamera setup but zoomed out a lot more. But it behaves like my freelookcamera

Fixed this by changing the X axis value back to 0. Got messed up somehow

It might be not switching because the Follow is not set

I tried that, but it still won’t switch. :frowning:

Post a screen of your Animator, along with the text of your PlayerDeathState

And it’s switching normally between the Freelook and Targeting camera?

When you die, which camera does it switch to? (or is it just stuck on whichever camera was in place?)

Yeah the switching based on the button press, from freelook to targeting and back to freelook works fine. But based on switching states it seems to not work? It goes back to the freelook camera it seems…
Wait a minute, maybe some exit state has freelook in it? (quickly checked, seems not the case)

It should be switching based on states now. We’re not telling the cameras to switch, we’re telling the Animator to switch, and the StateBasedCamera sees that.

Zip up your project and upload it to https://gdev.tv/projectupload. Be sure to remove the Library folder and any build folders (if you’ve built the game out) from the Zip to preserve space.

I won’t get to it right away, as I’m on the way out the door, but I’ll give it a look when I get back.

I uploaded it. Just to let you know ahead, I used a lot of placeholder animations since I still need to create them for my model. So you may see some warnings when you open the project and many of the animations are odd. For instance the impact animation and the jump animation etc. But the code works. I just need to figure out how I can switch cameras when the player dies. Oh and I’m using UNity 2020.3.7f1

Thank you so much for wanting to help! Curious to know what the issue is.

Hot time get it while it’s easy
Don’t mind come on up and see me
Rag Doll baby won’t you do me like you done before - Aerosmith, Ragdoll

It turns out the issue is the Ragdoll script! The Ragdoll script is turning off the animator before it has a chance to switch states to the PlayerDeath animation.

Here’s a patch that will delay turning off the Animator for .1 seconds so the Animator switches, then the Camera switches, and then the animator will turn off and the character will collapse.

Ragdoll.cs, no really!
using UnityEngine;

public class Ragdoll : MonoBehaviour
{
    [SerializeField] private Animator animator;
    [SerializeField] private CharacterController controller;
    private Collider[] allColliders;
    private Rigidbody[] allRigidbodies;

    private void Start()
    {
        allColliders = GetComponentsInChildren<Collider>(true);
        allRigidbodies = GetComponentsInChildren<Rigidbody>(true);
        ToggleRagdoll(false);
    }

    public void ToggleRagdoll(bool isRagdoll)
    {
        foreach (Collider collider in allColliders)
        {
            if(collider.gameObject.CompareTag("Ragdoll"))
            {
                collider.enabled = isRagdoll; // turns on the ragdoll if bool is true, off if false
                Debug.Log("Do I get here?");
            }
        }

        foreach (Rigidbody rigidbody in allRigidbodies)
        {
            if (rigidbody.gameObject.CompareTag("Ragdoll"))
            {
                rigidbody.isKinematic = !isRagdoll; // ragdoll is false means physics are applied and affect the rigidbody
                rigidbody.useGravity = isRagdoll;
            }
        }

        controller.enabled = !isRagdoll;
        if (isRagdoll)
        {
            Invoke(nameof(ShutoffAnimator), .1f);
        }
       //animator.enabled = !isRagdoll; // This was shutting off the animator before it could switch states
    }

    //Defer killing Animator so StateDrivenCamera can work.
    void ShutoffAnimator()
    {
        animator.enabled = false;
    }

}

Your assignment is to now fix the weights on the Rigidbodies and joints so the ragdoll doesn’t look absolutely horrible, and to adjust the death camera. You’ll see what I mean once it switches to ragdoll. :slight_smile:

That is awesome, Brian. Thank you for helping figuring that out! Did you perhaps upload the wrong script though? That’d the weapondamage.cs you shared. I’m curious as to what you adjusted! :slight_smile:
And yeah, hahah… I’ll still have to tweak a lot of things and create animations to make sure it doesn’t look like crap too much xD

Surely, you’re mistaken. Look again. :slight_smile: Ah, the power of gaslighting with the Edit button

Haha, I like your sense of humor. And you were right about the horrifying death camera, haha. Btw I really admire people like you who can just fix these kinds of things. I wish I had those skills.

I actually have one more issue I can’t figure out. Could you give me some pointers?

I created a blur effect through the global volume (render settings of the pipeline I’m using) and the blur effect only gets triggered when the enemy is in the chasing state. With other words, when it sees the player/when the player steps within its chasing range. I created a variable of type bool ‘enemyIsChasing’ in the EnemyStateMachine. Then in the EnemyChasingState’s Enter() method I set the variable to true, and in it’s exit method I set it to false. Then I got a script on the global volume to handle changes to the blur effect, called BlurEffectOnTargeting. This is it’s script:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using HauntedPSX.RenderPipelines.PSX.Runtime;
using UnityEngine.Rendering;

public class BlurEffectOnTargeting : MonoBehaviour
{

    private EnemyStateMachine enemyStateMachine;
    private EnemyStateMachine[] enemyStateMachines;
    public Volume volume;
    public float speed = 10f;
    private AccumulationMotionBlurVolume _motionBlurComponent;
    private float _timer;


    private void Awake()
    {
        volume = GetComponent<Volume>();
        volume.sharedProfile.TryGet(out _motionBlurComponent);
        _motionBlurComponent.weight.value = 0;

        enemyStateMachines = FindObjectsOfType<EnemyStateMachine>();
        //EnemyStateMachine[] enemyStateMachines = FindObjectsOfType<EnemyStateMachine>();

    }

    private void Update()
    {
    	foreach (EnemyStateMachine enemyStateMachine in enemyStateMachines) 
        { 
            if(enemyStateMachine.enemyIsChasing == true) 
            {
                //_motionBlurComponent.weight.value = Mathf.PingPong(_timer * speed, 1);
                _motionBlurComponent.weight.value = 0.7f;
                _timer += Time.deltaTime;
            }
            if(enemyStateMachine.enemyIsChasing == false)
            {
                _motionBlurComponent.weight.value = 0f;
            }
        }    
    }
}

Now, what I think I did is in the Awake state, find ANY gameobject that has the EnemyStateMachine component on it. And then in the update state I have a foreach loop checking if there is an object with this EnemyStateMachine on it in the scene, if so, set the enemyIsChasing bool to true and active the blur effect.

IT WORKS, but… it only works on the first enemy in the scene. It doesn’t seem to get triggered for the other enemies in the scene even though they have exactly the same components on them.

What could be the reason?

I understand if you don’t want to answer since its outside the scope of the course… but I thought I’d add to it to make it more of my own thing… Cant figure out why the code won’t run… If I disable the first enemy, it works on the other enemy… but always just on 1 enemy in the scene when I press play.

Thanks!

Privacy & Terms