Projectiles spawning with incorrect trajectory - c#

I wrote a script for gun and projectile but whenever I fire it only fires in the right direction when im pointing upwards, if i'm pointing to the sides it shoots downwards and if i'm pointing downwards it shoots up.
I've been trying to get a simple script that makes the gun rotate to face the mouse (works) and then to spawn bullets going in the firection of the gun, however, they spawn weirdly when not facing upwards, i've tried changing the object that has the script but nothing else since i'm not exactly sure what the error is.
Gun script:
using UnityEngine;
using System.Collections;
public class Gun : MonoBehaviour
{
public float offset;
public GameObject projectile;
public Transform shotPoint;
private float timeBtwShots;
public float startTimeBtwShots;
private void Update()
{
Vector3 difference = Camera.main.ScreenToWorldPoint(Input.mousePosition) - transform.position;
float rotZ = Mathf.Atan2(difference.y, difference.x) * Mathf.Rad2Deg;
transform.rotation = Quaternion.Euler(0f, 0f, rotZ + offset);
if (timeBtwShots <= 0)
{
if (Input.GetMouseButtonDown(0))
{
Instantiate(projectile, shotPoint.position, transform.rotation);
timeBtwShots = startTimeBtwShots;
}
}
else
{
timeBtwShots -= Time.deltaTime;
}
}
}
Projectile script:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Projectile : MonoBehaviour
{
public float pSpeed;
public float lifeTime;
public GameObject destroyEffect;
private void Start()
{
Invoke("DestroyProjectile", lifeTime);
}
private void Update()
{
transform.Translate(transform.up * pSpeed * Time.deltaTime);
}
void DestroyProjectile()
{
Destroy(gameObject);
}
}
I know that in the projectile script i change the transform.up inside the void update to transform.right or left the effect reverses and oly shoots correctly in the direction that I typed but I have no idead how to make it shoot properly in all directions.

I would hold a reference to the direction fired in the projectile and then move each frame based on that direction. So after we Instantiate the projectile, we calculate the direction Vector based on the gun/players rotation. The following code should do exactly what you are looking for, but is untested as I am currently using my phone! Hope this helps!
Inside Projectile.
public Vector3 directionFired;
Inside Gun.
GameObject proj = Instantiate(projectile, shotPoint.position, transform.rotation);
proj.directionFired = Quaternion.Euler(transform.rotation) * Vector3.forward;
timeBtwShots = startTimeBtwShots;
Inside Projectile Update
transform.Translate(directionFired * pSpeed * Time.deltaTime)

Related

GameObject reflecting off another gameObject error

I am new at Unity/c# and I wanted to make a pong game. I made this by watching a tutorial on youtube. There is no "error" except the ball doesn't move after touching the player.
This is ball code
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class BallCode : MonoBehaviour
{
private Rigidbody2D rb;
// Start is called before the first frame update
void Start()
{
rb = GetComponent<Rigidbody2D>();
}
// Update is called once per frame
void Update()
{
Vector2 position = transform.position;
position.x = position.x - 5.8f * Time.deltaTime;
transform.position = position;
}
}
This is ball bounce code:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class BallBounce : MonoBehaviour
{
private Rigidbody2D rb;
Vector3 lastVelocity;
// Start is called before the first frame update
void Awake()
{
rb = GetComponent<Rigidbody2D>();
}
// Update is called once per frame
void Update()
{
lastVelocity = rb.velocity;
}
private void OnCollisionEnter2D(Collision2D coll)
{
var speed = lastVelocity.magnitude;
var direction = Vector3.Reflect(lastVelocity.normalized, coll.contacts[0].normal);
}
}
And this is player code:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Player : MonoBehaviour
{
public float moveSpeed = 4.5f;
// Start is called before the first frame update
void Start()
{
}
// Update is called once per frame
void Update()
{
float vertical = Input.GetAxis("Vertical");
Vector2 position = transform.position;
position.y = position.y + moveSpeed * vertical * Time.deltaTime;
transform.position = position;
}
}
When I play the game the ball will collide with player, but it won't ricochet.
Your OnCollisionEnter2D method is not doing anything except set local variables that are quickly discarded. You need to make speed and direction variables of the BallCode or BallBounce class, then set up the BallCode class to use those variables in Update() when determining the motions it makes.
You can try adding a 2D rigid body property to the sphere and removing gravity.
Add a C# script to control the movement of the ball and add a 2D collider to the ball.
//Initial velocity
public float speed = 100f;
void Start()
{
this.GetComponent<Rigidbody2D>().AddForce
(Vector2.right * speed);
}
Add a 2D collider:
Add a 2D physical material to the sphere, so that the ball can bounce.
Modify 2D Physical Material Properties.
Added to the sphere's material.
Add player (Square) and control player movement script.
void Update()
{
// The mouse moves with the player
float y = Camer.main.ScreenToWorldPoint
(Input.mousePosition).y
this.transform.position = new Vector3
(transform.position.x,y,0);
}
Add the wall around the screen and the script Wall to control the randomness of the vertical speed and the direction of the ball when the ball collides with the wall.
public class Wall : MonoBehaviour
{
//Initial velocity
public float speed = 100f;
// Triggered when the collision ends
private void OnCollisionExit(Collision2D collision)
{
int r = 1;
if(Random.Range(0, 2) != -1)
{
r *= -1;
}
//add a vertical force
collision.gameObject.GetComponent<Rigidbody2D>().
AddForce(Vector2.up.*speed*r);
}
}
achieve effect:

Unity 2d Input lag

I'm making a 2d open world game with physics similar to that of stardew valley, but for some reason there's a lot of input lag on the character even when I remove all the other scripts and animations.
I even tried removing most of the sprites such as houses and whatnot but it still has a lot of lag, not framerate lag, just the player movement.
I will attempt to explain: If you just lightly tap the keyboard the player moves and stops just fine, but if you hold down the button then let go (for about 5s gives the most lag, doesn't get any worse after that), the player keeps moving a little after you let go of the key.
Here's the code:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class MovementControls : MonoBehaviour {
public float speed;
private Vector2 MoveSpeed;
private Rigidbody2D Player;
void Start() {
Player = GetComponent<Rigidbody2D>();
}
void Update() {
Vector2 PlayerInput = new Vector2(Input.GetAxis("Horizontal"), Input.GetAxis("Vertical"));
MoveSpeed = PlayerInput.normalized * speed;
}
void FixedUpdate() {
Player.MovePosition(Player.position + MoveSpeed * Time.fixedDeltaTime);
}
}
Anyone know how to fix this?
Here's what fixed the problem to anyone else with said problem:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class MovementControls : MonoBehaviour {
public float speed; //Change the player's speed
private Vector2 MoveSpeed; //This is what the player's speed will be set to after some math
private Rigidbody2D Player; //The player
void Start() {
Player = GetComponent<Rigidbody2D>(); //Find the player GameObject
}
void Update() {
Vector2 PlayerInput = new Vector2(Input.GetAxis("Horizontal"), Input.GetAxis("Vertical")); //Get input
MoveSpeed = PlayerInput * speed; //Math
Player.MovePosition(Player.position + MoveSpeed * Time.fixedDeltaTime); //Move the player
}
}

Rotate enemy character to see player character

I am making the enemy character to follow the player character.
In the FixedUpdate method the enemy character move toward the player character,
then in the Update method character rotates to the player character.
However, with this script, somehow enemy character is just nudging and gets stuck.
Where is the mistake, what's wrong???
public class enemy : MonoBehaviour
{
GameObject tObj;
private Vector3 latestPos;
public string targetObjectName;
public float speed = (float)1.0;
void Start()
{
tObj = GameObject.Find("player");
latestPos = transform.position;
}
void Update()
{
Vector3 diff = transform.position - latestPos;
latestPos = transform.position;
if (diff.magnitude > 0.01f)
{
transform.rotation = Quaternion.LookRotation(diff);
}
}
void FixedUpdate(){
Vector3 dir = (tObj.transform.position - this.transform.position).normalized;
float vx = dir.x * speed;
float vz = dir.z * speed;
this.transform.Translate((float)(vx / 50.0),0,(float)(vz / 50.0));
}
}
Use Package Manager "Standard Assets", Inside Unity put two FPSController one should be Player and the second can be Enemy.
I know this does not answers your question but its a faster way to ad Enemy.
AI Settings
Just remove the camera, Audio Source and First Person Controller Script as in image.
The Code for AI:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class FollowAI : MonoBehaviour
{
public CharacterController _controller;
public Transform target;
public GameObject Player;
[SerializeField]
float _moveSpeed = 2.0f;
// Use this for initialization
void Start()
{
}
// Update is called once per frame
void Update() {
Vector3 direction = target.position - transform.position;
direction = direction.normalized;
Vector3 velocity = direction * _moveSpeed;
_controller.Move(velocity * Time.deltaTime);
Vector3 lookVector = Player.transform.position - transform.position;
lookVector.y = transform.position.y;
Quaternion rot = Quaternion.LookRotation(lookVector);
transform.rotation = Quaternion.Slerp(transform.rotation, rot, 1);
}
}

2D - Firepoint not rotating consistently to aim at mouse

Followed brackeys tutorial for topdown shooter firing and although its working e.g the firepoint is rotating so it points towards the mouse its not happening consistently meaning it will stay pointed at a single spot for a few seconds before jumping towards the new spot. This delay before jumping to the new spot seems to be increased if i fire. Thanks in advance and sorry if this is a basic mistake as im new to C#
This is the Code i'm using to aim the firepoint.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class FirepointAim : MonoBehaviour
{
public Rigidbody2D rb;
public Camera cam;
Vector2 mousePos;
// Update is called once per frame 8
void Update(){
mousePos = cam.ScreenToWorldPoint(Input.mousePosition);
}
void FixedUpdate(){
Vector2 lookDir = mousePos - rb.position;
float angle = Mathf.Atan2(lookDir.y, lookDir.x) * Mathf.Rad2Deg - 90;
rb.rotation = angle;
}
}
And this is the code im using to fire.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Shooting : MonoBehaviour
{
public Transform firepoint;
public GameObject fireballPrefab;
public Rigidbody2D playerrb;
public float velocity = 20f;
public float push = 2f;
void Update(){
if(Input.GetButtonDown("Fire1"))
{
shoot();
}
}
void shoot()
{
GameObject shot = Instantiate(fireballPrefab, firepoint.position, firepoint.rotation);
Rigidbody2D rb = shot.GetComponent<Rigidbody2D>();
rb.AddForce(firepoint.up * velocity, ForceMode2D.Impulse);
playerrb.AddForce(firepoint.up * push * -1, ForceMode2D.Impulse);
}
}

Can't rotate and move at the same time

I'm currently developing an FPS shooter in Unity 3D. I'm fairly new to Unity and I've been having a bit of trouble with my player movement script. Individually everything seems to work, I can rotate and move the player freely, however when I try doing the two simultaneously my player seems to lock and won't rotate.
Sometimes jumping or moving to higher ground on the terrain seems to fix the issue, however I ran a few checks with gravity disabled, no colliders, and with the player well above ground, so the problem seems to be with the script. I've also done a bit of debugging and the Rotate() code does run, just the rotation amount doesn't seem to change.
Here is the player movement script:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
[RequireComponent(typeof(Rigidbody))]
public class PlayerMov : MonoBehaviour
{
[SerializeField]
private Camera cam;
[SerializeField]
private float speed = 5f;
[SerializeField]
private float looksensitivity = 4f;
[Header("Camera View Lock:")]
[SerializeField] //min and max amount for looking up and down (degrees)
private float lowlock = 70f;
[SerializeField]
private float highlock = 85f;
private Rigidbody rb;
private float currentrotx; //used later for calculating relative rotation
public Vector3 velocity;
public Vector3 rotation; // rotates the player from side to side
public float camrotation; // rotates the camera up and down
public float jmpspe = 2000f;
void Start()
{
rb = GetComponent<Rigidbody>();
}
// Update is called once per frame
void Update()
{
CalcMovement();
CalcRotation();
Rotate();
}
void FixedUpdate()
{
Move();
}
private void CalcRotation()
{
float yrot = Input.GetAxisRaw("Mouse X"); //around x axis
rotation = new Vector3(0f, yrot, 0f) * looksensitivity;
float xrot = Input.GetAxisRaw("Mouse Y"); //around y axis
camrotation = xrot * looksensitivity;
}
private void CalcMovement()
{
float xmov = Input.GetAxisRaw("Horizontal");
float zmov = Input.GetAxisRaw("Vertical");
Vector3 movhor = transform.right * xmov;
Vector3 movver = transform.forward * zmov;
velocity = (movhor + movver).normalized * speed;
}
void Move()
{
//move
if (velocity != Vector3.zero)
{
rb.MovePosition(rb.position + velocity * Time.fixedDeltaTime);
}
//jump
if (Input.GetKeyDown(KeyCode.Space))
{
//add double jump limit later!
rb.AddForce(0, jmpspe * Time.deltaTime, 0, ForceMode.Impulse);
}
}
void Rotate()
{
//looking side to side
rb.MoveRotation(rb.rotation * Quaternion.Euler(rotation));
// camera looking up and down
currentrotx -= camrotation;
currentrotx = Mathf.Clamp(currentrotx, -lowlock, highlock);
cam.transform.localEulerAngles = new Vector3(currentrotx, 0, 0);
}
}
Here are the relevant components attached to my player:
(The player has a couple more components attached but I ran tests without them and the problem still occurs)
Like I said I'm a bit of a unity novice, so i'm sure I missed something small but I just can't seem to place my finger on it, I've been stuck on this for a while so any help is much appreciated.
SOLVED:
It seems the problem I had was because I was running the scene from my laptop and not a desktop which I assume is what the Unity input was built for.

Categories