Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 11 Next capture
2021 2022 2023
1 capture
11 Jun 22 - 11 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
0
Question by Arclighter · Jul 28, 2015 at 07:34 AM · animatorloopboolean

Making a bool stay true for a second/while animation is playing

Hello, I'm a beginner at Unity, and am attempting to make a 2D Platform game. I'm making the Attacking Script for the player, but the problem is, I don't want the character to move at all when the player hits the attack button. As an example, I've set it up something like this:

The PlayerController script:

 using UnityEngine;
 using System.Collections;
 
 public class PlayerController : MonoBehaviour {
     
     public Rigidbody2D rb;
     public Animator anim;
     public float speed;
     public float jumpHeight;
     public Transform groundCheck;
     public LayerMask whatIsGround;
     public AttackController attackController;
 
     private bool stab;
     private bool upSwing;
     private bool downSwing;
     private bool sideSwing;
     private bool guarding;
 
     float groundRadius = 0.2f;
     public bool grounded = false;
     bool facingRight;
 
     void Start () {
     
         rb = GetComponent<Rigidbody2D> ();
         anim = GetComponent<Animator> ();
         facingRight = true;
         attackController = GameObject.Find ("Player").GetComponent<AttackController>();
     }
     
 
     void FixedUpdate () {
 
         float move = Input.GetAxis ("Horizontal");
         stab = attackController.stab;
         upSwing = attackController.upSwing;
         downSwing = attackController.downSwing;
         sideSwing = attackController.sideSwing;
 
         if (!sideSwing) {
         
                 if (move != 0 && grounded) {
                     rb.velocity = new Vector2 (move * speed, rb.velocity.y);
                     anim.SetBool ("IsWalking", true);
                 } else {
                     anim.SetBool ("IsWalking", false);
                 }
             }

And the AttackController script:

 using UnityEngine;
 using System.Collections;
 
 public class AttackController : MonoBehaviour {
 
     public Animator anim;
     public Rigidbody2D rb;
     public bool stab;
     public bool upSwing;
     public bool downSwing;
     public bool sideSwing;
     public PlayerController playerController;
     private bool OnGround;
 
     void Start () {
         anim = GetComponent<Animator> ();
         rb = GetComponent<Rigidbody2D> ();
         playerController = GameObject.Find ("Player").GetComponent<PlayerController>();
 
     }
     
 
     void Update () {
 if (Input.GetKeyDown (KeyCode.X) && (Input.GetKey (KeyCode.RightArrow) || Input.GetKey (KeyCode.LeftArrow))&& OnGround) {
             anim.SetTrigger ("SideSwing");
             sideSwing = true;
             Debug.Log ("Player is SideSwing");
         } else {
             sideSwing = false;
 }


Now the PlayerController script can access the sideSwing bool from AttackController script, so that when sideSwing is true, the movement code will not run. The problem is, when the player has GetKeyDown on the X key, the bool is only true for a single FixedUpdate frame, and can still move while the animation plays from the animator.

Changing it to just GetKey will work, but only if the player is holding down the key, and that's unnecessary in a platformer. I've been considering putting the bool in some kind of loop so that it stays true for a limited time, like one second or even the animation clip. But because I'm using an Animator I don't know how to get the length of the current animation being played. I also don't know how to make the bool stay in a time loop without using coroutines, and I'm not sure how to implement that.

Perhaps there's a simpler way to do this, and I'm not seeing it.

Comment
Add comment · Show 2
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image _Gkxd · Jul 28, 2015 at 07:58 AM 0
Share

Couldn't you just see if the animation is playing using Animator.GetBool?

avatar image Arclighter · Jul 29, 2015 at 04:17 PM 0
Share

Well the animation is played using a trigger, which I prefer to keep that way. But I guess if I need to, I can change it to a bool and do that.

2 Replies

· Add your reply
  • Sort: 
avatar image
3
Best Answer

Answer by GiyomuGames · Jul 28, 2015 at 07:43 AM

Why don't you want to use a coroutine to keep your bool true for 1 second? Otherwise in the animation window you could have your "swing" animation set a bool to true when it starts and set it back to "false" when it ends.

Coroutines are very interesting tools and are not complicated.

You can write a coroutine as below:

 private IEnumerator SideSwingCo()
 {
     sideSwing = true;
     anim.SetTrigger ("SideSwing");
     // Wait for 1 second
     yield return new WaitForSeconds(1);
     sideSwing = false;
 }

Then your Update method becomes:

 void Update () {
     if (Input.GetKeyDown (KeyCode.X) && (Input.GetKey (KeyCode.RightArrow) || Input.GetKey (KeyCode.LeftArrow))&& OnGround) {
         StartCoroutine(SideSwingCo());
  }



Comment
Add comment · Show 5 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image Arclighter · Jul 29, 2015 at 04:14 PM 0
Share

I suppose I'm not familiar enough with coroutines to use them. Coroutines go in loops right? Even if coroutines will suspend the bool for a second, if there's a less complex method, I want to try that out first, such as your other suggestion. Thanks!

avatar image getyour411 · Jul 29, 2015 at 05:21 PM 1
Share

You should pause, get some coffee or your beverage of choice, and commit to learning Coroutines. They have endless uses and there many really good examples in UA of how to set them up. Yes the first takes time, but you'll be glad you did once you 'get it' and start using them.

avatar image GiyomuGames · Jul 30, 2015 at 10:40 AM 1
Share

I agree with getyour411. Coroutines are very interesting tools and are not complicated.

You can write a coroutine as below:

 private IEnumerator SideSwingCo()
 {
     sideSwing = true;
     anim.SetTrigger ("SideSwing");
     // Wait for 1 second
     yield return new WaitForSeconds(1);
     sideSwing = false;
 }

Then your Update method becomes:

 void Update () {
     if (Input.Get$$anonymous$$eyDown ($$anonymous$$eyCode.X) && (Input.Get$$anonymous$$ey ($$anonymous$$eyCode.RightArrow) || Input.Get$$anonymous$$ey ($$anonymous$$eyCode.LeftArrow))&& OnGround) {
         StartCoroutine(SideSwingCo());
  }



avatar image Arclighter · Jul 30, 2015 at 06:09 PM 0
Share

Thank you! It seems to be working well. I'll take both of your advice and learn more about corountines.

avatar image GiyomuGames · Jul 31, 2015 at 05:20 AM 0
Share

Cool! I updated my initial answer accordingly so you can mark it as correct.

avatar image
1

Answer by NeverHopeless · Jul 28, 2015 at 08:45 AM

I would advice to don't reset sideSwing in else part of your code in AttackController.cs. Instead use animation events to call a function on animation completion and set sideSwing to false there.

AttackController.cs

 public void OnSideSwingCompletion()
 {
     sideSwing = false;
 }

 void Update () {
  if (Input.GetKeyDown (KeyCode.X) && (Input.GetKey (KeyCode.RightArrow) || Input.GetKey (KeyCode.LeftArrow))&& OnGround) {
              anim.SetTrigger ("SideSwing");
              sideSwing = true;
              Debug.Log ("Player is SideSwing");
          } 
  }

Now Select you game object and goto Animation tab select last frame and press Add Event button and pick the function OnSideSwingCompletion.

Another thing you should probably consider that when you set state in PlayerController.cs script as:

 anim.SetBool ("IsWalking", false);

Do not forget to set the velocity of rigid body to zero, otherwise it may keep moving as per the applied force.

 anim.SetBool ("IsWalking", false);
 rb.velocity = Vector3.zero;

Hope it helps!

Comment
Add comment · Show 2 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image Arclighter · Jul 29, 2015 at 04:12 PM 0
Share

Thanks, but when I do attempt to add an event, I only functions from the PlayerController script are listed. Do I need to do something else to see the functions of the AttackController script?

avatar image NeverHopeless · Jul 29, 2015 at 05:11 PM 0
Share

Create a function in playercontrollerscript and use Send$$anonymous$$essage function to send a call to attackcontrollerscript.

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

5 People are following this question.

avatar image avatar image avatar image avatar image avatar image

Related Questions

Animation Loop 2 Answers

Animator trigger keeps retriggering. 0 Answers

How to make a 2d animation repeat 1 Answer

how do i make a loop for a boolean? 2 Answers

Double collision on "ground" tagged object results in player thinking they're in air? 1 Answer


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges