- Home /
Smooth movement using Rigidbody2d
Hi everyone! Trying to make my objects in 2d game move smoothly, but they are moving jerky. Using unity answers i've made: 1. Edit ->project settings -> Time: fixed timestep and maximum allowed timesetp is 0.0166666 2. Used only atlases, so the number of draw calls in scene is now about 5-6. 3. Fps in scene is now about 1200-1500. 4. Tried to use transform.position,transform.translate,rigidbody2d.addforce,rigidbody2d.velocity,etc. The same result. 5. Tried to use Update,FixedUpdate,LateUpdate,Coroutines. 6. Vsync is turned off. But still one time per second there'is a small "freeze" in a screen. The same problem on Android device. Here's a simple script:
public float shark_speed = 1;
public float left_turn_range = -5;
public float right_turn_range = 5;
float leftBorder, rightBorder, coord;
int flag = 1;
public GameObject shark,left_border_obj,right_border_obj;
int i = 1;
private Vector3 cameracoords_right_corner, camera_coords_left_corner,vector_direction,pos;
public Rigidbody2D rigbody;
// Use this for initialization
void Start()
{
rightBorder = right_border_obj.transform.position.x;
camera_coords_left_corner = Camera.main.ViewportToWorldPoint(new Vector3(0, 1, 0));
leftBorder = left_border_obj.transform.position.x;
rigbody.velocity = new Vector2(shark_speed,0);
pos = new Vector3(rightBorder, this.transform.position.y, 0);
}
// Update is called once per frame
void FixedUpdate()
{
rigbody.velocity = new Vector2(rigbody.velocity.x, 0);
}
void Update()
{
coord = transform.position.x;
if (transform.position.x >= rightBorder)
{
rigbody.velocity = new Vector2(-rigbody.velocity.x, 0);
transform.Rotate(0, 180, 0);
if (transform.rotation.y > 180)
transform.rotation = Quaternion.Euler(0, 0, 0);
}
if (transform.position.x <= leftBorder)
{
flag = 1;
transform.Rotate(0, -180, 0);
rigbody.velocity = new Vector2(-rigbody.velocity.x, 0);
}
}
What am i doing wrong? Thx for any tips.
Answer by EvilSam · Dec 30, 2015 at 03:51 AM
i suspect one of two reasons for this:
First, the easy way, open profiler window and see if there is a hiccup like these:
if so, then you can see what is causing this hiccup by clicking on these peaks, and continue from there.
Second, the most likely, there are a few things to correct in the code posted above:
when dealing with physics always use FixedUpdate, I don't consider it a good practice to split that code into Update and FixedUpdate
Why do you assign rigbody.velocity to itself in FixedUpdate? is it to reset y component? if so i think you just need to add a constraint to the rigid body instead.
the checks in Update will be executed many times in between fixed updates when the frame rate is higher than fixed frame rate, so when you exceed the right border, you negate the velocity vector, and then before physics update is executed, update will be executed again, negating the velocity vector again, restoring it to it's original value, and this sort of behavior makes it possible for your object to stick just outside the right edge for undefined time. to solve that try checking the sign of rigbody.velocity.x before negating.
so instead of
if (transform.position.x >= rightBorder)
try
if (transform.position.x >= rightBorder && rigbody.velocity.x > 0)
Tried to use Interpolate/Extrapolate in Rigidbody2d, but the problem is still here. Opend profiler and there's a hiccup:
As far as i know, these are standart Unity methods, causes this hiccup: Gfx.WaitForPresent(60-65%), TextRendering.CleanUp(25-35%) , sometimes Camera.Render(10%)
Second part:
I splitted the code into update and FixedUpdate, because i've seen this in unity tutorial (flappy bird tutorial in 2dgame pack). But i can make all code in FixedUpdate , but the problem is still here
The same answer). I've seen this in the same tutorial and i was pretty suprised, but decided to follow this tutorial. Here's the code of tutorial:
void Update() { //don't allow control if the bird has died if (isDead) return; //look for input to trigger a "flap" if (Input.any$$anonymous$$eyDown) flap = true; } void FixedUpdate() { //if a "flap" is triggered... if (flap) { flap = false; //...tell the animator about it and then... anim.SetTrigger("Flap"); //...zero out the birds current y velocity before... GetComponent<Rigidbody2D>().velocity = new Vector2(GetComponent<Rigidbody2D>().velocity.x, 0); //..giving the bird some upward force GetComponent<Rigidbody2D>().AddForce(new Vector2(0, upForce)); } }
Thx for finding my mistake. I'll fix it. But the problem isn't solved.
looking at your profiler screenshot, I think that your actual problem is generating too much load on the Garbage Collector, because for every rendering peak there is a drop in "Total GC Allocated", are you creating skid-marks, particles, etc... more info about what else in the scene you have would prove useful.
you can try removing everything from your scene one by one (and you can try commenting out some parts of your scripts in order to do so), until the problem disappears, then you would know what's the cause, but one thing for sure, it's not a RigidBody2D issue, the script seems fine and should work without any problems (after fixing the check mentioned in 3)
It became a little better when I used Application.targetFrameRate = 60;
, and became much better when i set Fixed timestep to 0.008. But, as i know, i shouldn't do this. The scene is empty, there is no particles,etc.
Answer by Uberlion · Dec 30, 2015 at 04:37 AM
well... You and i clearly have different ideas of simple movement scripts, take an example:
public float speed = 1234;
void FixedUpdate() { float input = Input.GetAxis("Verticl");
Getcomponent().AddForce(gameObject.transform.up speed input); }
^ as far as i know, it moves up and down relevant to the character. So wherever the front of the character is facing it goes forward. I think... might want to have a look at the script first.
Try messing with that and adding in a turning script, it worked fine for me. i added some Linear Drag myself though, prevents sliding.
Unless you're looking for something entirely different. In which case ignore me. I'm pretty nooby anyway.
EDIT: Almost forgot, it's the sides that are making your script go screwy. Can't be bothered to learn why.