Take the 2-minute tour ×
Game Development Stack Exchange is a question and answer site for professional and independent game developers. It's 100% free, no registration required.

This days I'm trying to create a 2D character controller with unity (using phisics). I'm fairly new to physic engines and it is really hard to get the control feel I'm looking for. I would be really happy if anyone could suggest solution for a problem I'm finding:

This is my FixedUpdate right now:

public void FixedUpdate()
{
    Vector3 v=new Vector3(0,-10000*Time.fixedDeltaTime,0);
    _body.AddForce(v);

    v.y=0;
    if(state(MovementState.Left))
    {
        v.x=-_walkSpeed*Time.fixedDeltaTime+v.x;
        if(Mathf.Abs(v.x)>_maxWalkSpeed) v.x=-_maxWalkSpeed;
    }
    else if(state(MovementState.Right))
    {
        v.x= _walkSpeed*Time.fixedDeltaTime+v.x;
        if(Mathf.Abs(v.x)>_maxWalkSpeed) v.x=_maxWalkSpeed;
    }

    _body.velocity=v;

    Debug.Log("Velocity: "+_body.velocity);
}

I'm trying here to just move the rigid body applying a gravity and a linear force for left and right. I have setup a physic material that makes no bouncing and 0 friction when moving and 1 friction with stand still. The main problem is that I have colliders with slopes and the velocity changes from going up (slower) , going down the slope (faster) and walk on a straight collider (normal). How could this be fixed? As you see I'm applying allways same velocity for x axis.

For the player I have it setup with a sphere at feet position that is the rigidbody I'm applying forces to.

Any other tip that could make my life easier with this are welcomed :).

P.D. While coming home I have noticed I could solve this applying a constant force parallel to the surface the player is walking, but don't know if it is best method.

share|improve this question
4  
Old school platformers used hand tuned "cartoon physics" for jumping mechanics and direct speed control (ie. no physics at all) for walking movement. If you can rewrite the character controller, do so, because it's going to be difficult to poke and prod a squishy physics simulation into the crisp movements that old school games had. –  Patrick Hughes Jun 15 '12 at 10:08
    
The problem of writting a custom one is that collision detection is lost. And it is not easy to rebuild it without using raycast (depending on the environment, etc... it could be a bunch of them). How do you handle this situations? –  Notbad Jun 15 '12 at 11:56
    
You can have colliders on things that are still custom animated- when you use kinematic rigidbodies. I'd warrant that in most situations you don't really want real-world physics / forces etc for this sort of application. If you're looking for a more technical angle, perhaps research Human IK –  Runonthespot Aug 1 '12 at 13:26
    
Def ditch physics in this situation. –  Ray_Garner Mar 25 at 7:00
add comment

4 Answers 4

If you are looking to mimic old school platformers step one is to ditch physics altogether. You will end up fighting the physics system to get the decidedly non-realistic motion of an old school platformer. Have a look at this CharacterController replacement that ditches physics altogether to get a good idea of one way to implement it.

share|improve this answer
    
Thanks a lot prime. Good job as always! –  Notbad Mar 25 at 13:33
add comment

You'd probably be happier going with what mheona recommended. But if you're going to use Unity's physics, then you probably want to use ForceMode.VelocityChange.

Example:

public void FixedUpdate()
{
    var v = Vector3.zero;
    if(state(MovementState.Left))
    {
        v.x=-_walkSpeed*Time.fixedDeltaTime+v.x;
        if(Mathf.Abs(v.x)>_maxWalkSpeed) v.x=-_maxWalkSpeed;
    }
    else if(state(MovementState.Right))
    {
        v.x= _walkSpeed*Time.fixedDeltaTime+v.x;
        if(Mathf.Abs(v.x)>_maxWalkSpeed) v.x=_maxWalkSpeed;
    }

    _body.AddForce(v, ForceMode.VelocityChange);

    Debug.Log("Velocity: "+_body.velocity);
}

You should also apply global gravity in your project's Physics settings, and for objects that you want to fall faster, add a Constant Force component.

ForceMode.Impulse is similar but is affected by the rigidbody's mass. Makes it harder to tune.

share|improve this answer
add comment

Even if you dislike the built in Character Controller component(as I do), take a look at the Unity's example code for the 2D Gameplay Tutorial.

The code implements a complete 2D gameplay with moving platforms, enemies and boxes with collision, using the Character Controller.

But if you dont even want to take a look, I suggest you to minimize the use of physics and try to copy its behaviour with your own code. Depending on what kind of 2D game you are planning it may work pretty good. For instance, instead of applying force to Rigidbody.velocity to move your character you could mess directly with Transform.Translate(), which moves the object Transform.position based on its axis. You could determine the forward and back related to the object itself or maybe the platform or floor Transform.up, so you will know if its a ramp and kind of know its angle.

Also if you create some sort of speed control atributte(e.g. how long the key is pressed) you can apply it together with your direction while translating to prevent your character walking something too much inclined without some speed, much like they did on Sonic the Hedgehog for Genesis/Mega Drive.

If you choose to keep using physics I can't help you at all because I'm not so good at it, but be aware that it's a normal behaviour to go 'up a slope' slower as the body needs more force to keep up, like real life.

share|improve this answer
    
The first thing I read when I got into unity was that tutorial. The problem is that the control feel is pretty bad. This is why I wanted to find my own solution. On the other hand when you commen about using the Transform.Translate() it is not that easy to do slopes and other things. You must ray cast several times (2 or 3 for the floor, more for the direction your are moving depending on the hero size). For mobile devices raycast is not good, and less if yo ahve to do 5..n per collision detection iteration. Perhaps I could be wrong, but I don't think so. –  Notbad Sep 21 '12 at 6:24
add comment

What you want it the built in Character Controller. By setting the step offset property on this component you can get a player to move up and down slopes with ease.

share|improve this answer
    
Sorry for not commenting I knw there's a Character Controller in unity and that I have used it several times, but I don't like how it behaves. It is more suited for just FPS not a platform game where motion mechanics are one of the most importnat things. –  Notbad Jan 17 '12 at 8:06
    
I think once you fiddle with the settings on the Character Controller it works well. What did you find lacking? –  NoobsArePeople2 Jan 17 '12 at 17:27
    
First thing I don't like is that it is slow relative to usual rigid bodies with some ray cast. Knowing how to achieve it, I think I could do a more lightweight controller. Another problem is that being a capsule/sphere odd behaviour at platform edges (it can be solved with some more ray casts). This is why I want to roll my own. –  Notbad Jan 17 '12 at 18:31
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.