Search Unity

  1. Unity 2019.1 is now released.
    Dismiss Notice

Firing a retractable object

Discussion in 'Scripting' started by BitRei, May 20, 2019.

  1. BitRei

    BitRei

    Joined:
    Jan 15, 2018
    Posts:
    63
    I'm making a game where the player's main tool is a large claw they fire from a gun and retract. It's in 3D. I have tried many things, but the main problem is that though AddForce works the best, it is inconsistent. More consistent methods I've used will not fire out a set distance, or if they do you have to be perfectly facing along the z axis for it to work. Help?

    Code (csharp):
    1.  
    2. using System.Collections;
    3. using System.Collections.Generic;
    4. using UnityEngine;
    5. public class ClawController : MonoBehaviour
    6. {
    7.     public GameObject claw;
    8.     Rigidbody claww;
    9.     public bool fired = false;
    10.     public float zzz;
    11.     public float distance;
    12.     public float stopping;
    13.     public float stoppingnz;
    14.     public float stoppingx;
    15.     public float stoppingnx;
    16.     public Transform holdPoint;
    17.     // Start is called before the first frame update
    18.     void Start()
    19.     {
    20.         zzz = 0;
    21.     }
    22.     // Update is called once per frame
    23.     void Update()
    24.     {
    25.         claww = claw.GetComponent<Rigidbody>();
    26.         claww.transform.position = new Vector3(claww.transform.position.x, holdPoint.position.y, claww.transform.position.z);
    27.         if (Input.GetKeyDown(KeyCode.E) && fired == false)
    28.         {
    29.             fired = true;
    30.         } else if (Input.GetKeyDown(KeyCode.E) && fired == true)
    31.         {
    32.             claww = claw.GetComponent<Rigidbody>();
    33.             claww.transform.position = holdPoint.position;
    34.             fired = false;
    35.         }
    36.         if (fired)
    37.         {
    38.             if(zzz != stopping)
    39.             {
    40.                 claww.AddForce(transform.forward * 10);
    41.                 zzz = zzz + 0.5f;
    42.             }
    43.         } else if (fired == false)
    44.         {
    45.             zzz = 0;
    46.         }
    47.     }
    48.     /*void Fire()
    49.     {
    50.         stopping = holdPoint.position.z + distance;
    51.         stoppingnz = holdPoint.position.z - distance;
    52.         stoppingx =
    53.     }*/
    54. }
    55.  
    56.  
     
  2. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    6,174
    AddForce is designed to be used during FixedUpdate(), not Update, which is why it's inconsistent - the length of an Update frame varies based on the framerate, but FixedUpdate is always constant, and AddForce adds force across the entire length of the frame.

    Best solutions here would be:
    1) in place of your current AddForce call, just set some boolean flag instead, and then:
    Code (csharp):
    1. void FixedUpdate() {
    2. if (yourBooleanFlag) {
    3. claww.AddForce(transform.forward * 10f);
    4. yourBooleanFlag = false;
    5. }
    2) Move all of your Update logic into FixedUpdate (I probably wouldn't recommend this as handling input in FixedUpdate gets tricky)
    3) Just set claww.velocity directly.
     
  3. BitRei

    BitRei

    Joined:
    Jan 15, 2018
    Posts:
    63
    Thanks! That works really well. The only problem now is that is won't stop moving now.
     
  4. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    6,174
    Did you forget to set the boolean flag to false after you use it once, maybe?
     
  5. BitRei

    BitRei

    Joined:
    Jan 15, 2018
    Posts:
    63
    No.
    Code (csharp):
    1.  
    2. if (Input.GetKeyDown(KeyCode.E) && fired == false)
    3.         {
    4.             fired = true;
    5.             pew = true;
    6.         } else if (Input.GetKeyDown(KeyCode.E) && fired == true)
    7.         {
    8.             claww = claw.GetComponent<Rigidbody>();
    9.             claww.transform.position = holdPoint.position;
    10.             claww.transform.rotation = holdPoint.rotation;
    11.             fired = false;
    12.         }
    13.        if (fired)
    14.         {
    15.             if (zzz != stopping)
    16.             {
    17.                 pew = true;
    18.                 zzz = zzz + 0.5f;
    19.             }
    20.         }
    21.         else if (fired == false)
    22.         {
    23.             pew = false;
    24.             zzz = 0;
    25.         }
    26.     }
    27.     private void FixedUpdate()
    28.     {
    29.         if(pew == true)
    30.         {
    31.             claww.AddForce(transform.forward * 10);
    32.             pew = false;
    33.         }
    34.     }
    35.  
    36.  
     
  6. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    6,174
    Lines 15-18 look like trouble. You may be having some float precision problems with that comparison to "stopping", which would cause zzz to never == stopping, and pew would keep getting set to true. Try if zzz < stopping instead?
     
  7. BitRei

    BitRei

    Joined:
    Jan 15, 2018
    Posts:
    63
    It still doesn't work, and works the same even if I don't include that entire segment of code. I thing what is happening is that either even if pew is false it still adds force, or the left over force makes it keep going. I can try having it so that regardless if pew = false, it can stop. I think what I'd need to do is remove/set any current velocity to absolute 0 but idk how to do that.
     
  8. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    6,174
    Well, yes. Adding force will give it momentum, which will keep it moving until something else acts on it.

    Two easy options, depending on how you want the game to "feel":
    1) When you want it to stop moving, set claww.velocity to 0.
    2) In the claw's Rigidbody in the Unity Editor, give it some Drag.
     
  9. BitRei

    BitRei

    Joined:
    Jan 15, 2018
    Posts:
    63
    The drag option works!