Hi, I have a problem when I held the attack button of my character. I have a shoot animation, but I only want it to be displayed once the shot is fired and not while I’m holding the button down.
This is my code:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Move : MonoBehaviour {
public float maxSpeed = 30;
public float speed = 5.0f;
public bool isOnground;
Transform _transform;
Rigidbody2D rb;
Animator anim;
public float jumpVelocity;
public float fallm = 3.5f;
public float lowJumpm = 3f;
//BALA
public Transform firePoint;
public GameObject Bala;
public GameObject Bala2;
public float chargetimer = 0;
public KeyCode chargeshoot;
public GameObject Charge;
// Use this for initialization
void Start () {
rb = GetComponent <Rigidbody2D> ();
anim = GetComponent <Animator> ();
}
// Update is called once per frame
void Update () {
//Move
anim.SetFloat("velX", Mathf.Abs(rb.velocity.x));
anim.SetBool ("Grounded", isOnground);
//Salto
if (Input.GetButtonDown ("Jump") && isOnground) {
rb.velocity = Vector2.up * jumpVelocity;
anim.SetBool ("shooting",false);
}
if (rb.velocity.y < 0) {
rb.velocity += Vector2.up * Physics2D.gravity.y * (fallm - 1) * Time.deltaTime;
} else if (rb.velocity.y > 0 && !Input.GetButton ("Jump")) {
rb.velocity += Vector2.up * Physics2D.gravity.y * (lowJumpm - 1) * Time.deltaTime;
}
}
void FixedUpdate (){
//Move
float h = Input.GetAxis("Horizontal");
if (h > 0.1f) {
transform.localScale = new Vector3 (1f, 1f, 1f);
}
if (h < -0.1f) {
transform.localScale = new Vector3 (-1f, 1f, 1f);
}
rb.AddForce (Vector2.right * speed * h);
float limitedSpeed = Mathf.Clamp (rb.velocity.x, -maxSpeed, maxSpeed);
rb.velocity = new Vector2 (limitedSpeed, rb.velocity.y);
//Shoot
if (Input.GetKeyDown (KeyCode.A)) {
Instantiate (Bala, firePoint.position, firePoint.rotation);
if (Input.GetKeyDown (KeyCode.A) && isOnground) {
anim.SetBool ("shooting", true);
}
}
if (Input.GetKey (chargeshoot)) {
chargetimer += Time.deltaTime;
}
if(Input.GetKeyUp (chargeshoot) && (chargetimer > 1) ) {
Instantiate (Bala2, firePoint.position, firePoint.rotation);
chargetimer = 0;
anim.SetBool ("shooting",false);
}
if(Input.GetKeyUp (chargeshoot) && (chargetimer < 1)) {
anim.SetBool ("shooting",false);
chargetimer = 0;
}
}
(This isn’t the problem you are actually facing, but i want to tell you there is a problem in your script
Checking for Input in fixedUpdate might lead to the input being ignored because inputs get calculated during the Update. Fixed update gets called 50 times a second (usually), Update sometimes gets called faster. If you Input “A”, there is some times an entire frame end before fixedUpdate gets called.)
This is an old code i am using (it isn’t perfect (the naming part and the crossinput part are totally wrong) and it’s only a part of it but it has some ideas about how to make input to work better when using it in fixed update.
Code
public partial class PlatformerCharacterVX
{
[Header("@~~~~Input Settings (PlatformerCharacterInput.cs)")]
[SerializeField] private List<string> buttons;
[Header("_Inspector debugging")]
public List<Inputbutton> buttonlist;
partial void StartInput()
{
buttonlist = new List<Inputbutton>();
foreach(string str in buttons)
{
buttonlist.Add(new Inputbutton(str));
}
var trigone = new Inputbutton("r2");
trigone.isTrigger = true;
var trigtwo = new Inputbutton("l2");
trigtwo.isTrigger = true;
buttonlist.Add(trigone);
buttonlist.Add(trigtwo);
}
partial void UpdateInput()
{
foreach(Inputbutton buto in buttonlist)
{
buto.SetActualValue();
}
}
partial void FixedUpdateInput()
{
foreach (Inputbutton buto in buttonlist)
{
if (Getbutton(buto.name, inputtype.down))
{
foreach(InterfacePlayerAddon addon in addons)
{
addon.Button(buto.name, inputtype.down);
}
}
buto.getchangedbyfixedupdate();
}
}
public bool Getbutton(string name,inputtype type)
{
if(type== inputtype.normal)
{
// Debug.Log(buttonlist.Find(a => a.name == name).name + "(actual)" + buttonlist.Find(a => a.name == name).actualvalue.ToString());
return buttonlist.Find(a => a.name == name).actualvalue;
}
else if (type == inputtype.down)
{
//Debug.Log(buttonlist.Find(a => a.name == name).name + "(down)" + buttonlist.Find(a => a.name == name).buttondown.ToString());
return buttonlist.Find(a => a.name == name).buttondown;
}
else
{
// Debug.Log(buttonlist.Find(a => a.name == name).name + "(up)" + buttonlist.Find(a => a.name == name).buttonup.ToString());
return buttonlist.Find(a => a.name == name).buttonup;
}
}
public enum inputtype
{
normal,
down,
up
}
}
public class Inputbutton
{
public string name;
public bool actualvalue;
public bool previousvalue;
public bool isTrigger;
public bool buttondown;
public bool buttonup;
public bool gotchangedByFixedInput;
public Inputbutton(string name)
{
this.name = name;
}
public void SetActualValue()
{
previousvalue = actualvalue;
if (!isTrigger)
actualvalue = CrossPlatformInputManager.GetButton(name + "button");
else
actualvalue = CrossPlatformInputManager.GetAxis(name + "trigger") > 0.1f;
if (gotchangedByFixedInput)
{
if (!previousvalue & actualvalue)
{
buttondown = true;
}
else if (previousvalue & !actualvalue)
{
buttonup = true;
}
}
}
public void getchangedbyfixedupdate()
{
buttondown = false;
buttonup = false;
gotchangedByFixedInput = true;
}
}
I don’t know what your charging feature keycode is, is it “A” too ?
I’m not sure i understood your problem, is the shoot animation called too early?
Is the shoot animation still called after your character stopeed shooting?
Yeah the key code is A too and I’m doing a character that can charge his attack just like megaman, but the problem is that when I hold down the button to charge the attack my character stays in the shoot animation.
In the animator , make the shooting animation to last for something like 0.2 seconds, and to be launched by a trigger.
Instead of anim.SetBool, use anim.SetTrigger. Or maybe you can find a way to make the animator itself set the bool to false after some time.
Another way of doing it would be to add a timer inside your script itself. (the code i will show you is a crappy code, find a better way of doing it , it’s better in the animator)
public float shootimer = 0;
void Update()
{
if(Input.GetKeyDown(chargeshoot)
{
//Instantiate the sutff;
//if is on the ground
shootimer = 0.2;
}
if(shootimer >0)
{
anim.SetBool("shooting",true);
shootimer -= Time.deltaTime;
}
else
{
anim.SetBool("shooting",false);
}
}