I have been having some problems with animating my 2D player to simply play a short animation when the left arrow key is pressed and the same with the right arrow key, after the the keys are pressed I want it to go back to the idle animation. I have 3 bool parameters, Isleft, Isright, Isidle. I have been struggling with this for a few days now and was wondering if anyone knows how to actually make this work.
I have been trying everything by trial and error changing the code and changing the conditions in the animator window
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.SceneManagement;
public class Movement : MonoBehaviour
{
public float speed = 6.0f;
public GameObject character;
private Animator anim;
private Scene scene;
void OnTriggerEnter2D(Collider2D other)
{
if (other.gameObject.tag == "Enemy")
{
SceneManager.LoadScene(0);
}
else
{
}
}
/*void OnCollisionEnter2D(Collision2D collision)
{
switch (collision.gameObject.tag)
{
case "Enemy":
Destroy(gameObject);
break;
default:
//nothing
break;
}
}*/
void Start()
{
anim = GetComponent<Animator>();
scene = SceneManager.GetActiveScene();
}
void Update()
{
if (Input.anyKey)
{
transform.Translate(Vector3.forward * Time.deltaTime * speed);
}
// Move Right
if (Input.GetKey(KeyCode.RightArrow) || (Input.GetKey(KeyCode.D)))
{
transform.position += Vector3.right * speed * Time.deltaTime;
anim.SetBool("Isright", true);
}
//Move Left
if (Input.GetKey(KeyCode.LeftArrow) || (Input.GetKey(KeyCode.A)))
{
transform.position += Vector3.left * speed * Time.deltaTime;
anim.SetBool("Isleft", true);
}
else
{
anim.SetBool("Isidle", true);
}
}
}
You don't set booleans to false and this last "else" block refers to LeftArrow/A. If you are not holding either of them, Isidle is true.
Related
I have a character, he can move and jump. I need to check if it is grounded, so I made a trigger box collider as a characters component, and I use OnTriggerEnter and OnTriggerExit to check if it is grounded, but the exit of collision with object that the character is standing on is detected one physics update late, and when it is detected, the upward velocity appears to become 0, and the character starts falling. Here is my code:
using System.Collections;
using UnityEngine;
public class Player : MonoBehaviour
{
public float speed = 4.0f;
public float jumpSpeed = 8.0f;
private bool doJump = false;
private Rigidbody rb;
bool isGrounded = false;
private float x, z;
private void Awake()
{
rb = GetComponent<Rigidbody>();
}
private void Update()
{
x = Input.GetAxis("Horizontal");
z = Input.GetAxis("Vertical");
if (Input.GetKeyDown(KeyCode.Space))
{
StartCoroutine(Jump());
}
}
void FixedUpdate()
{
if (isGrounded)
{
//this is movement
rb.velocity = (transform.right * x) * speed * Time.fixedDeltaTime + (transform.forward * z) * speed * Time.fixedDeltaTime;
}
if (isGrounded && doJump)
{
doJump = false;
rb.AddForce(0, jumpSpeed, 0, ForceMode.VelocityChange);
}
}
IEnumerator Jump()
{
//need the coroutine to make the player jump even if space pressed a bit earlier than
//the character landed
doJump = true;
yield return new WaitForSeconds(0.15f);
doJump = false;
}
private void OnTriggerStay(Collider other)
{
if (other != this.gameObject)
{
isGrounded = true;
}
}
private void OnTriggerExit(Collider other)
{
if (other != this.gameObject)
{
isGrounded = false;
}
}
}
I tried to not use coroutine for jumping but it doesn't help. What helps is deleting the movement line.
I think you are trying to implement "Pre_Update" function, I have found this solution maybe you can use it:
https://answers.unity.com/questions/614343/how-to-implement-preupdate-function.html
I am not sure but I think if you initialize your physics component in the Start function instead of the Awake function then it might work.
I am trying to add particles to my Collison but I receive errors. I keep getting his error from my code and I don't know why. The errors are: OnGUIDepth changed: was 0 is 1. Event type was 0 (56,60): error CS1001: Identifier expected. (56,55): error CS1003: Syntax error, ',' expected
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PlayerController1 : MonoBehaviour
{
public float horizontalInput;
public float speed = 10.0f;
public float xRange = 100;
private Animator playerAnim;
public AudioClip crashSound;
private AudioSource playerAudio;
public GameObject projectilePrefab;
public ParticleSystem explosionParticle;
public bool isOnGround = true;
public bool gameOver;
// Start is called before the first frame update
void Start()
{
playerAudio = GetComponent<AudioSource>();
}
// Update is called once per frame
void Update()
{
if (transform.position.x < -xRange)
{
transform.position = new Vector3(-xRange, transform.position.y, transform.position.z);
}
if (transform.position.x > xRange)
{
transform.position = new Vector3(xRange, transform.position.y, transform.position.z);
}
else
{
}
horizontalInput = Input.GetAxis("Horizontal");
transform.Translate(Vector3.right * horizontalInput * Time.deltaTime * speed);
if (Input.GetKeyDown(KeyCode.Space))
{
//Instantiate(projectilePrefab, transform.position, projectilePrefab.transform.rotation);
Instantiate(projectilePrefab, transform.position, transform.rotation);
}
}
private void OnCollisionEnter(Collision collision other)
{
if (other.gameObject.CampareTag("Rock"))
{
isOnGround = true;
} else if (other.gameObject.CompareTag("Star"))
{
Debug.Log("Game Over");
gameOver = true;
playerAnim.SetBool("Death_b", true);
playerAnim.SetInterger("DeathType_int", 1);
explosionParticle.Play();
playerAudio.PlayOneShot(crashSound, 1.0f);
}
}
}
Is there anything I need to fix in my code?
The errors here are already stated by the compiler and are an easy fix, just hover your mouse over and see what intellisense tells you
Let's go over this function
private void OnCollisionEnter(Collision collision other)
{
if (other.gameObject.CampareTag("Rock"))
{
isOnGround = true;
}
else if (other.gameObject.CompareTag("Star"))
{
Debug.Log("Game Over");
gameOver = true;
playerAnim.SetBool("Death_b", true);
playerAnim.SetInterger("DeathType_int", 1);
explosionParticle.Play();
playerAudio.PlayOneShot(crashSound, 1.0f);
}
}
In the first line, the
private void OnCollisionEnter(Collision collision other)
'other' makes no sense to be there. The Collision is the type, and collision is the identifier. People often put other as the identifier which you might have gotten confused. Seeing you are using other as the variable in the function, you can remove collision from the brackets.
The function further contains just spelling errors, such as .CampareTag which needs to be CompareTag
Please strictly follow syntax and use intellisense, it is an incredible tool which will 100% eliminate such errors.
The other error (if an error at all, seems like just a log)
OnGUIDepth changed: was 0 is 1. Event type was 0 (56,60):
is not contained within this script.
Don't know what I'm am doing wrong here, I am trying to trigger an animation in unity
Edit: The problem is not that the enemy is destroyed before the animation plays, as the enemy doesn't even get destroyed when
player.cs
private void OnCollisionEnter2D(Collision2D collision)
{
if (collision.gameObject.tag == "Enemy")
{
Blue blue = collision.gameObject.GetComponent<Blue>();
if (action == State.jump || action == State.fall)
{
blue.JumpedOn();
blue.Death();
jumpVelocity = multiplier * jumpVelocity;
rb.velocity = Vector2.up * jumpVelocity;
}
}
}
enemy.cs
public void JumpedOn(){
action = State.death;
anim.SetBool("Death", true);
}
public void Death() {
Destroy(this.gameObject);
}
have the condition set in the animator window too, if death = true play animation
see here
when I remove the
blue.JumpedOn();
the other lines will run correctly
blue.Death();
jumpVelocity = multiplier * jumpVelocity;
rb.velocity = Vector2.up * jumpVelocity;
You need to put a delay between JumpedOn() and Death() because you are calling them in the same frame, the object gets destroyed before the animation has a chance to play. A good way to do this would be coroutines, which are very valuable to use for delaying execution of code.
private IEnumerator coroutine;
IEnumerator WaitAndDestroy(GameObject _callingObject, float _waitTime)
{
yield return new WaitForSeconds(_waitTime);
_callingObject.Destroy();
}
public void Death() {
coroutine = WaitAndDestroy(gameObject, 1.5f);
StartCoroutine(coroutine);
}
I think you should try adding some delay between blue.JumpedOn(); and blue.Death();.
So, I am trying to create a soccer game from scratch... all I have done until now, is setting up the ball. This is how I want it to work: When the player collides with the ball, the ball jumps forward a bit. If you start running the ball will be pushed further away.
Now, here is my script for the ball (I am using the standard FPSController as character):
using UnityEngine;
using System.Collections;
public class BallController : MonoBehaviour {
private Rigidbody rb;
public GameObject character;
public float moveSpeed = 1000;
public float shootSpeed = 2000;
bool isTurnedUp = false;
bool isTurnedDown = false;
bool done = false;
// Use this for initialization
void Start () {
rb = GetComponent<Rigidbody>();
}
// Update is called once per frame
void FixedUpdate () {
//Debug.Log(isTurnedUp + ", " + isTurnedDown);
switch (character.GetComponent<UnityStandardAssets.Characters.FirstPerson.FirstPersonController>().m_IsWalking)
{
case true:
if (isTurnedUp == false)
{
moveSpeed = moveSpeed / 1.4f;
isTurnedUp = true;
isTurnedDown = false;
}
break;
case false:
if (isTurnedDown == false)
{
moveSpeed = moveSpeed * 1.4f;
isTurnedDown = true;
isTurnedUp = false;
}
break;
}
}
void Update()
{
if (Input.GetMouseButtonDown(0))
{
if (Vector3.Distance(gameObject.transform.position, character.transform.position) <= 5)
{
float distance = Vector3.Distance(gameObject.transform.position, character.transform.position);
}
}
}
void OnCollisionEnter(Collision collision) {
FixedUpdate();
if (done == false) {
rb.AddForce(Vector3.forward * moveSpeed, ForceMode.Impulse);
done = true;
}
else {
done = false;
}
}
//other
void OnDrawGizmosSelected()
{
Gizmos.color = Color.yellow;
Gizmos.DrawWireSphere(transform.position, 2);
}
}
My problem is that the ball doesn't behave how I want it... it feels like it's about luck if the ball will jump forward when I touch it. Can someone tell me what I did wrong?
Inside of OnCollisionEnter you need to ensure the ball can only be kicked by the player. You can check whether or not the player has collided with the ball by checking the name or tag of the collision. The following example uses the name and assumes your player GameObject is named "Player".
Remove the done flag since this will only allow the player to kick the ball every other time they collide, and remove the FixedUpdate() call since FixedUpdate() is already called automatically every physics calculation.
Finally, if you want to kick the ball away from the player, then you need to calculate the direction away from the collision point instead of using Vector3.forward as seen below.
void OnCollisionEnter(Collision collision)
{
if(collision.gameObject.name == "Player")
{
Vector3 direction = (collision.transform.position - transform.position).normalized;
rb.AddForce(-direction * moveSpeed, ForceMode.Impulse);
}
}
I'm not so good with Visual Studio.
I'm making a simple game and my gameobject (player) should move up when Space or Left Mouse Button is pressed.
Here is my code
using UnityEngine;
using System.Collections;
public class PixelMovement : MonoBehaviour {
Vector3 velocity = Vector3.zero;
public Vector3 PressVelocity;
public float maxSpeed = 5f;
public float fowardSpeed = 1f;
bool didPress = false;
// Use this for initialization
void Start () {
}
//Do Graphic & Input updates
void update() {
if(Input.GetKeyDown(KeyCode.Space) || Input.GetMouseButtonDown(0)) {
didPress = true;
}
}
//Do physics engine updates here
void FixedUpdate () {
velocity.x = fowardSpeed;
if (didPress == true){
didPress = false;
velocity += PressVelocity;
}
velocity = Vector3.ClampMagnitude(velocity, maxSpeed);
transform.position += velocity * Time.deltaTime;
}
}
So, it should move like contrary to gravity. And when it stops holding, it continues to fall. I already have gravity I just need that "Up movement"
//Do Graphic & Input updates
void update() {
if(Input.GetKeyDown(KeyCode.Space) || Input.GetMouseButtonDown(0)) {
didPress = true;
}
}
I think the problem is because update() should be Update()
Try:
//Do Graphic & Input updates
void Update() {
if(Input.GetKeyDown(KeyCode.Space) || Input.GetMouseButtonDown(0)) {
didPress = true;
}
}
This is a quick fix: You're calling Input.GetKeyDown() and Input.GetMouseButtonDown() which only return true on the first frame that the button is pressed.
If you want a repeating event (I.E., the mouse button or space is held down), use Input.GetKey(KeyCode.Space) and Input.GetMouseButton(0).