Search Unity

Force field

Discussion in 'Getting Started' started by Monkey-Mihawk, Dec 3, 2019.

  1. Monkey-Mihawk

    Monkey-Mihawk

    Joined:
    Dec 3, 2019
    Posts:
    1
    Hi,
    I'm new on Unity and I try to do my first own basic game ! There is a feature I want to put in my game : force field.
    Under condition I want when my player enter in a trigger zone a force is applied on him upward and make him fly sinusoidally without touching floor anymore.
    My problem is more the force is strong, more he go far away top and faster he fall. When he eventually fall into my force field kinetic energy is to important and my player pass my force field..

    Code (CSharp):
    1. public float forceFieldST;
    2.  
    3. private void OnTriggerStay(Collider other)
    4.     {
    5.         if (other.gameObject.CompareTag("forceField"))
    6.         {
    7.             playerRB.AddForce(Vector3.up * forceFieldSt, ForceMode.Acceleration);
    8.         }
    9.     }
    Hope you have solution for me and hope my English is not to bad for you to understand my problem :)
     
    Last edited: Dec 3, 2019
  2. Olmi

    Olmi

    Joined:
    Nov 29, 2012
    Posts:
    589
    Hi,

    Please, start using code tags, it's not much more effort needed. You can find it in the message editor on the right side, next to where it says "Code:". Makes the code content so much more readable.

    Well, I don't have time at the moment to test your code, but considering you didn't tell (or show) much more about the details of your Physics setup, I suggest you first try to add some Drag to your RigidBody in the object you are moving by adding force. You could also add some fake-ish multiplier that you apply to your rigidbody's velocity.

    And to make the added amount of force consistent, you should do it in FixedUpdate call, which is the update for physics simulation things. Otherwise you can get inconsistent results.
     
    Joe-Censored likes this.
  3. Joe-Censored

    Joe-Censored

    Joined:
    Mar 26, 2013
    Posts:
    6,924
    Yeah, don't do this in OnTriggerStay, as that is tied to your frame rate, which means on faster computers you'll get more calls to OnTriggerStay, and more force applied, than you do on slower computers. Just set a bool in OnTriggerStay and apply the force in FixedUpdate.

    As for applying too much force, you could try checking the upward velocity of the character, which is the Y component of Rigidbody.velocity. Then only add more force if the upwards velocity is below a certain threshold. Maybe something like below, but you'll have to play with the numbers.

    Code (CSharp):
    1. public float forceFieldST;
    2. private bool addForceFieldEffect = false;
    3. public float MaxForceFieldY = 0.5f;
    4.  
    5.  
    6. private void OnTriggerStay(Collider other)
    7. {
    8.     if ((other.gameObject.CompareTag("forceField")) && (playerRB.velocity.y < MaxForceFieldY))
    9.     {
    10.         addForceFieldEffect = true;
    11.     }
    12. }
    13.  
    14. void FixedUpdate()
    15. {
    16.     if (addForceFieldEffect)
    17.     {
    18.         playerRB.AddForce(Vector3.up * forceFieldSt, ForceMode.Acceleration);
    19.         addForceFieldEffect = false;
    20.     }
    21. }

    https://docs.unity3d.com/ScriptReference/Rigidbody-velocity.html

    You could also consider making the force much higher if you see the velocity.y is significantly in the negative (meaning falling very fast). Or you could try just setting velocity directly when falling fast, like cutting Y velocity in half each FixedUpdate above a certain fall speed, so it looks like you hit a hard pillow no matter how fast you're falling, then just let AddForce take over again when falling slow enough. Play around with it and see what really works for you.
     
    Last edited: Dec 3, 2019