Gravity Direction Change

Hey there everyone!

Long time reader, first time poster! :slight_smile: Nice to meet you all :slight_smile:

I’m currently having a problem in Unity figuring out code to change the direction of gravity on a Character Controller. By this I mean the gravity normally is facing downwards, as gravity normally does, so my character can run left, right and jump as I want him to but I want to be able to change it so the gravity faces upwards so the character can walk and jump on the roof. As my beautiful image attached tries to show. :slight_smile:

Any help of guidance would truly be brilliant and much appreciated!!!

I’ve had a look around on the forums and not found anything particularly similar, but then again I am a man and stereotyping myself I can’t find anything.

Many Thanks,

Matthew :slight_smile:

EDIT: http://www.youtube.com/watch?v=FxuacwotoQw&feature=related This in essence is what I am attempting to achieve from the game VVVVVV :slight_smile:

444925--15473--$artisticbrilliance.png

Well you could use script to disable the player character’s gravity and then apply “custom gravity” (movement) which would push him in certain direction, in this case upwards :slight_smile:

Unity - Scripting API: ← Script reference on gravity. Or you can do it in newbie fashion, like I would, and just apply enough constant opposite push like with jump

you cannot rotate the built in character controller. You can use a rigid body character controller.
http://forum.unity3d.com/threads/53490-FPS-Rigidbody-Controller

1 Like

afaik He didn’t require rotating the character controller, he only needed ability to jump to ceiling and walking there :slight_smile:

Yea pretty much what i want to be able to do is run around on the ground right, left and jump then when i press a button the gravity (in whatever sense of technical terms in unity gravity means) switches so my character will move to the ceiling but I will still be able to move right left and jump (jumping obviously being in the opposite direction now) :slight_smile:
x

Character controllers are controlled purely through script.
Instead of .Move()ing your character down along Y, move them up. Voila, reverse gravity. :slight_smile:

it is implied that the character controller will be rotated when you walk on the ceiling :slight_smile: Which you cannot do with the built in character controller, but you can very easily do with a custom rigid body controller in the link that I posted. The gravity change there would also be very easy since it’s applied manually:

this can be rewritten as

rigidbody.AddForce(gravityDirection * gravity * rigidbody.mass);

where gravityDirection is a unit vector like Vector3(0,-1,0);
then you only change the gravityDirection vector to change gravity.
Another way would be to keep the built in character contoroller and rotate the entire world relative to the player.
It depends on the situation.

1 Like

I haven’t read the whole thread, but strictly speaking, walking on the ceiling instead of the floor does not require that the character controller be rotated.

The character controller relies very much on whether it is grounded or not. As I said above, you could device a solution where you rotate the entire world so that the character walks on the ceiling, but you need to have the bottom of the character controller be touching the surface you are walking on. (gravity pointing towards the bottom of the controller). Otherwise it won’t work.

I actually very much hope that someone will prove me wrong here (with and example), since it will be very useful for me too, to get the built in character controller to walk on walls or ceiling.

Character Controllers are the completely wrong tool for this situation. A normal rigidbody, and custom Gravity solution should work, though. You want to avoid the Physics.gravity completely on this.

First, some background - on the rigidbody, uncheck “Use Gravity”, but make sure “Freeze Rotation” is checked. You want the rigidbody to have mass and drag both, of course. I rarely use Angular Drag, but if you have a use for it, go ahead.

Now the fun point of this code is when you hit the button you choose to flag as the “gravity flipper”,

var gravity : float = -9.81;
var flipSpeed : float;

var flipKey : KeyCode;

function FixedUpdate()
{
  if( Input.GetKey( flipKey ) )
  {
    FlipMe();
  }

  // You may wish to modify this.  The key point,
  // though, is that the gravity gets applied locally
  // to the attached rigidbody/transform.
  transform.Translate(  0,gravity,0 );
}

function FlipMe()
{
  // You can recode this to be a coroutine,
  // perhaps that flips the player a bit more
  // gracefully.
  transform.Rotate( 180, 0,0 );
}

Walking on walls (that is, surfaces that are not parallel to the XZ plane) is another matter, but couldn’t you use the ‘collisionFlags’ field to determine whether the object is ‘grounded’ when walking ‘upside-down’?

Rather then using gravity wouldn’t it be better to turn it off and add your own constant force component on the player? Unless of course you wanted the entire world to be effected by the gravity change.

Just wanted to say thanks for all the help and guidance everyone! Where having a mess around with it now since were pretty new to Unity and I’ll post back when we get it working! So good to see a forum filled with such a helpful community! :smile:

Many Thanks,

Matthew :slight_smile:

hi, when i try to use this script i seem to just keep falling/glitching through the walls,

any reason to why?

Because it’s 5 years old? No, but really, the script was only one small part of the solution presented. Did you follow the other parts? Also, you can use a completely normal rigidbody now and just change the global direction of gravity if you like, which wasn’t possible I don’t believe when this topic was made.

1 Like

Thanks for replying; it’s crazy that A) I have code on these forums that has been a thing for 5 years, B) that I ever used UnityScript, and C) how I used to code.

Still, the code should work, given the other bits like configuring the Rigidbody.

1 Like

I know this is very old but since I was working on this, it might help somebody else. I needed to use the Character Controller and still allow walking on ceilings with inverted gravity, and it is possible with a workaround:

  • Character Controller doesn’t support actual rotation and will still return not grounded even if grounded on the ceiling and rotated appropriately
  • Simply write a custom IsCustomGrounded() function and make sure it returns character.isGrounded when normal gravity
  • When in inverted gravity, rotate the Character Controller, inverse your gravity code to make sure everything is inverted (vertical movement, jump, gravity, etc.)
  • Make sure IsCustomGrounded() does not return character.isGrounded when gravity is inverted, but rather return (character.collisionFlags & CollisionFlags.Above) != 0; to check if there is a contact above the character instead of checking the Below flag, and it will work fine!

Cheers