How can I Stop my 2D Character from Gliding After Movement - c#

I am currently making a 2D top down survival game. I have coded the player controller and it works good other than one issue that bugs the crap out of me! My character doesn't stop moving (or decelerates very slowly) whenever I stop pressing the movement keys. How can I make it so that it stops immediately, if not nearly immediately? Any tips help thanks!
Here is the code i'm using!
using UnityEngine;
using System.Collections;
public class CharacterMovement : MonoBehaviour{
public float speed;
private Rigidbody2D rb2d;
void Start ()
{
rb2d = GetComponent<Rigidbody2D> ();
}
void FixedUpdate()
{
float moveHorizontal = Input.GetAxisRaw ("Horizontal");
float moveVertical = Input.GetAxisRaw ("Vertical");
Vector2 movement = new Vector2 (moveHorizontal, moveVertical);
rb2d.AddForce (movement * speed);
}
}

I have figured out a way to increase the Deceleration. I scrapped my code and changed the mechanics so that the Character follows the mouse and moves forward with the "W" key or the up arrow. This smoothed the directional changes and made gameplay more enjoyable, as for the deceleration, I solved the problem by making the Linear Drag in the rigidbody2D inspector more than one and increasing the speed to make up for velocity loss.
Here is my code for future answer seekers!
using UnityEngine;
using System.Collections;
public class CharacterMovement : MonoBehaviour{
public float speed;
private Rigidbody2D rbtd;
void Start ()
{
rbtd = GetComponent<Rigidbody2D> ();
}
void FixedUpdate()
{
var mousePosition = Camera.main.ScreenToWorldPoint (Input.mousePosition);
Quaternion rot = Quaternion.LookRotation(transform.position - mousePosition,
Vector3.forward);
transform.rotation = rot;
transform.eulerAngles = new Vector3 (0, 0, transform.eulerAngles.z);
rbtd.angularVelocity = 0;
float input = Input.GetAxis ("Vertical");
rbtd.AddForce (gameObject.transform.up * speed * input);
}
}

Related

Why is my Player moving Down on Screen In Unity

I am not sure why but I am starting a new project in which a player moves with WASD and points towards the mouse pointer. This is all the code I have so far as It is only early into development but any help would be nice. Here is a little pic of what I currently have on my player...
ANY HELP WILL BE AMAZING!
using System.Collections.Generic;
using UnityEngine;
public class PlayerMovement : MonoBehaviour
{
public float moveSpeed = 5f;
public Rigidbody2D rb;
Vector2 movement;
// Update is called once per frame
void Update()
{
movement.x = Input.GetAxisRaw("Horizontal");
movement.y = Input.GetAxisRaw("Vertical");
Vector3 mousePosition = Input.mousePosition;
mousePosition = Camera.main.ScreenToWorldPoint(mousePosition);
Vector2 direction = new Vector2(
mousePosition.x - transform.position.x,
mousePosition.y - transform.position.y
);
transform.up = direction;
}
private void FixedUpdate()
{
rb.MovePosition(rb.position + movement * moveSpeed * Time.fixedDeltaTime);
}
}
Set the gravity scale to 0 or set Rigidbody2D body type to Kinematic.
Kinematic rigidbodies can only be moved via script and are not participated in regular physics unlike dynamic rigidbody. So if you don't want some 'automatic' behaviors always use kinematic body type, otherwise if only problem is automatic 'moving down' issue then set gravity scale to 0 and that's all.
I think both will work in your case. And also here is some further info

I have followed a tutorial on making controls for a fps game on unity. the controls work but if I leave the controls then I keep moving to the left

enter image description hereI have made controls for my character to move along the X axis. They seem to be working fine but my character keeps moving left and I'm not sure why or what I have missed.I have posted code from the two separate scripts
I have rechecked his code several times.I have checked to see if my arrow keys, numpad keys and WASD are sticking or any other.
using UnityEngine;
[RequireComponent(typeof(Rigidbody))]
public class PlayerMotor : MonoBehaviour
{
private Vector3 velocity = Vector3.zero;
private Rigidbody rb;
void Start()
{
rb = GetComponent<Rigidbody>();
}
//gets a movement vector
public void Move (Vector3 _velocity)
{
velocity = _velocity;
}
//run every physics iteration
void FixedUpdate()
{
PerformMovement();
}
//perform movement based on velocity variable
void PerformMovement ()
{
if (velocity != Vector3.zero)
{
rb.MovePosition(rb.position + velocity * Time.fixedDeltaTime);
}
}
}
And the controller:
using UnityEngine;
[RequireComponent(typeof(PlayerMotor))]
public class PlayerController : MonoBehaviour
{
[SerializeField] //makes speed show up in inspector even if set to private
private float speed = 5f;
private PlayerMotor motor;
void Start ()
{
motor = GetComponent<PlayerMotor>();
}
void Update()
{
//Calculate movement velocity as a 3D vector
float _xMov = Input.GetAxisRaw("Horizontal");
float _zMov = Input.GetAxisRaw("Vertical");
Vector3 _movHorizontal = transform.right * _xMov;
Vector3 _movVertical = transform.forward * _zMov;
//final movement vector
Vector3 _velocity = (_movHorizontal + _movVertical).normalized * speed;
//apply movement
motor.Move(_velocity);
}
}
I expect 0 output when not pressing buttons but it seems to make me move to the left at speed of 5
You have a controller connected and reporting a slight movement in one direction. Use Input.GetAxis instead of Input.GetAxisRaw to let Unity handle deadzone detection. This way, nearly neutral inputs will be treated as neutral inputs.
void Update()
{
//Calculate movement velocity as a 3D vector
float _xMov = Input.GetAxis("Horizontal");
float _zMov = Input.GetAxis("Vertical");
Vector3 _movHorizontal = transform.right * _xMov;
Vector3 _movVertical = transform.forward * _zMov;
//final movement vector
Vector3 _velocity = (_movHorizontal + _movVertical).normalized * speed;
//apply movement
motor.Move(_velocity);
}

How to rotate camera around player in unity c#

I need to rotate the camera around my player gameobject while holding the left mouse button. How would I approach this?
Also, I've read a bit on Vector 3, but I don't have a full understanding of it. Anybody who could explain it would be greatly appreciated.
I've looked at youtube videos and this one is exactly the concept I was looking for. I was just having trouble applying it to my code.
I'm on a bit of a time crunch, exams are nearing and my teacher hasn't explained most things that are explained in the video.
// This is my code inside the camera which follows the ball/player
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ScriptBallCam : MonoBehaviour
{
public GameObject player;
private Vector3 offset;
void Start()
{
offset = transform.position - player.transform.position;
}
void LateUpdate()
{
transform.position = player.transform.position + offset;
}
//End of code inside camera
//Code inside of player/ball
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ScriptBall : MonoBehaviour
{
public float speed;
private Rigidbody rb;
void Start()
{
rb = GetComponent<Rigidbody>();
}
void FixedUpdate()
{
float moveHorizontal = Input.GetAxis("Horizontal");
float moveVertical = Input.GetAxis("Vertical");
Vector3 movement = new Vector3(moveHorizontal, 0.0f, moveVertical);
rb.AddForce(movement * speed);
}
// end code
Results I'm expecting are exactly shown at 1:22 in
https://www.youtube.com/watch?v=xcn7hz7J7sI
Try this. The script goes on your camera.
Basically this script works by first getting the direction your mouse has moved in. In this case the X axis Mouse X (left/right direction). Then we take our rotation speed turnSpeed, and use it to rotate around the player by that amount of degrees using Quaternion.AngleAxis. Finally we make sure that the camera is always looking at the player by using transform.LookAt
using UnityEngine;
using System.Collections;
public class OrbitPlayer : MonoBehaviour {
public float turnSpeed = 5.0f;
public GameObject player;
private Transform playerTransform;
private Vector3 offset;
private float yOffset = 10.0f;
private float zOffset = 10.0f;
void Start () {
playerTransform = player.transform;
offset = new Vector3(playerTransform.position.x, playerTransform.position.y + yOffset, playerTransform.position.z + zOffset);
}
void FixedUpdate()
{
offset = Quaternion.AngleAxis (Input.GetAxis("Mouse X") * turnSpeed, Vector3.up) * offset;
transform.position = playerTransform.position + offset;
transform.LookAt(playerTransform.position);
}
}
There is a lot of information on this topic over here:
https://answers.unity.com/questions/600577/camera-rotation-around-player-while-following.html

Problem with Jumping with Translate function [Unity 2D]

Soo, I'm trying to code a simple Platformer as a work for class, and I'm having problems with the jumping, the character actually jumps but it seems as a teleport since it instantly reaches the peak of the jump and then gradually falls, I'd like to make it smoother.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class playerMovement : MonoBehaviour {
public float speed;
public float jumpForce;
public bool grounded;
public Transform groundCheck;
private Rigidbody2D rb2d;
// Use this for initialization
void Start () {
rb2d = GetComponent<Rigidbody2D>();
}
// Update is called once per frame
void Update () {
}
private void FixedUpdate()
{
float moveVertical = 0;
float moveHorizontal = Input.GetAxis("Horizontal") * speed;
moveHorizontal *= Time.deltaTime;
grounded = Physics2D.Linecast(transform.position, groundCheck.position, 1 << LayerMask.NameToLayer("Ground"));
if (grounded && Input.GetKeyDown("space"))
{
moveVertical = Input.GetAxis("Jump") * jumpForce;
moveVertical *= Time.deltaTime;
}
Vector2 move = new Vector2(moveHorizontal, moveVertical);
transform.Translate(move);
}
}
The answer to the question is below, however, for future questions related to Unity ask on the Unity forum. You will get a better answer quicker as more people are focused on Unity itself.
To fix your jump, rather split your vertical and horizontal movement in two parts and use your rigidbody you assigned in in your Start() function to handle jumping. Use ForceMode.Impulse to get an instant burst of speed/acceleration.
private void FixedUpdate()
{
float moveHorizontal = Input.GetAxis("Horizontal") * speed;
moveHorizontal *= Time.deltaTime;
grounded = Physics2D.Linecast(transform.position, groundCheck.position, 1 << LayerMask.NameToLayer("Ground"));
if (grounded && Input.GetKeyDown("space"))
{
rb2d.AddForce(transform.up * jumpForce, ForceMode.Impulse);
}
Vector2 move = new Vector2(moveHorizontal, 0);
transform.Translate(move);
}
Instead of setting the position when you jump, add a vertical impulse to the character's rigidbody with:
if (grounded && Input.GetKeyDown("space"))
{
moveVertical = Input.GetAxis("Jump") * jumpForce;
moveVertical *= Time.fixedDeltaTime;
rb2d.AddForce(moveVertical, ForceMode.Impulse);
}
Vector2 move = new Vector2(moveHorizontal, 0f);
This will let Rigidbody2D handle the work of altering the vertical velocity on each frame.
Also, since you are doing all of these calculations in FixedUpdate, instead of Update, there is no sense in using Time.deltaTime. You should be using Time.fixedDeltaTime instead.

2D Ricochet Physics not working in Unity

I am trying to make a game where a ball will be ricocheting off several different colliders on screen. Based on what I researched I got some code that seemed to make sense at first but does not seem to work at all. I am testing it out just by having the ball fall down onto a 2D floor with a box collider attached to it. However once it collides with the floor it just stops there and doesn't bounce back up. I tried disabling "Queries Start in Colliders" in the project settings and offsetting the origin position of the RaycastHit2D so that it would not detect the collider its attached to but that still didn't work. I don't think the RaycastHit2D is working at all because it doesn't even display anything in the console. Here is my code:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class EnemyBehavior : MonoBehaviour {
Rigidbody2D rigidbody;
public Vector2 startPos;
public float speed;
public float hitOffset;
Vector3 vector = new Vector3(0, 5,0); //used to offset origin point of RaycastHit2D hit
private void OnEnable()
{
rigidbody = GetComponent<Rigidbody2D>();
this.transform.position = startPos;
}
private void Update()
{
transform.Translate(Vector2.down * speed * Time.deltaTime);
RaycastHit2D hit = Physics2D.Raycast(transform.position + vector, - transform.up, speed * Time.deltaTime + hitOffset);
Debug.DrawRay(transform.position, -transform.up, Color.red);
Ray2D ray = new Ray2D(transform.position, -transform.up);
if (hit)
{
Debug.Log(speed * Time.deltaTime + hitOffset);
Debug.Log(hit.collider.name);
Vector2 reflectDir = Vector2.Reflect(ray.direction,hit.normal);
float rotation = Mathf.Atan2(reflectDir.y, reflectDir.x) * Mathf.Rad2Deg;
transform.eulerAngles = new Vector3(0, 0, rotation);
}
}
}
Is my math bad? Any help is very appreciated, thanks.

Categories

Resources