Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 13 Next capture
2021 2022 2023
1 capture
13 Jun 22 - 13 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
0
Question by bergerinc · Feb 27, 2014 at 04:56 PM · rigidbodybulletprojectile

2D bullet changes direction based on player's world position?

I'm like a lot of people here in that I'm fairly new to Unity. I'm having an issue that I just can't seem to figure out. I've tried a bunch of examples instantiating and moving a projectile in a top down 2d shooter.

My problem is that the projectile will fire in a different direction based on my player's world position. If the player is in a negative x or y axis then the bullet will fire in the reverse direction. If the player is in a positive x or y axis then it will fire as intended. Also, the closed the player is to the center of the world, the projectile fires slower.

I would appreciate any help!

Here is the code:

[code]

 public GameObject projectilePrefab;
 public float projectileSpeed = 2.0f;
 public float projectileLifeSpan = 10.0f;

 private Transform myTransform;
 private Vector3 shootDirection;
 private Vector3 spawnPoint;

 private bool isShooting = false;



 void Update(){

     //set global variables
     this.myTransform = transform;
     this.spawnPoint = this.myTransform.Find("ProjectileSpawnPoint").position;
     
     //shoot
     this.isShooting = (Input.GetButtonDown ("Fire1"));
 
 }


 void FixedUpdate () {

     //shoot
     if (this.isShooting) {

         //instantiate projectile at spawn point
         GameObject projectile = GameObject.Instantiate (this.projectilePrefab, this.spawnPoint, Quaternion.identity) as GameObject;

         //add force to move
         projectile.rigidbody.AddForce(this.myTransform.position * this.projectileSpeed, ForceMode.Impulse);

         //kill object after delay
         Destroy(projectile, this.projectileLifeSpan);

     }

 }

[/code]

Comment
Add comment
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

2 Replies

· Add your reply
  • Sort: 
avatar image
0

Answer by ben-tmg · Feb 27, 2014 at 05:31 PM


    //add force to move
    projectile.rigidbody.AddForce(this.myTransform.position * this.projectileSpeed, ForceMode.Impulse);

This line creates force depending on the players position. This means the closer the player is to the origin (0,0,0) the lower the force.

If you always want the bullet to go in the same direction then you need to give it the same Vector. ie If you want it to always travel along positive X you would do:

 var xDir = new Vector3(1f, 0f, 0f);
 projectile.rigidbody.AddForce(xDir * this.projectileSpeed, ForceMode.Impulse);

You wouldn't want to create the Vector every frame, you would want to create it in Start or Awake and save it.

Also, you don't need to save the variables myTransform and spawnPoint every frame in Update, you only need to do it Start.

Comment
Add comment · Show 3 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image bergerinc · Feb 27, 2014 at 06:10 PM 0
Share

Thanks for the reply ben-tmg.

I don't think I can use a vector in that way since the player is constantly moving and rotating. I moved the get on the spawn position into the shooting section so it is only updated when a shooting request in handled.

I guess my question now is really how do I apply uniform force to the projectile (so it doesn't go slower or faster based on position) and that the projectile applies force only in the direction the player is facing at the time the projectile is instantiated.

updated code:

[code]

 public GameObject projectilePrefab;
 public float projectileSpeed = 2f;
 public float projectileLifeSpan = 10f;

 private Transform myTransform;
 private Vector3 shootDirection;
 private Vector3 spawnPoint;

 private bool isShooting = false;


 void Start(){
     //set global variables
     this.myTransform = transform;

 }

 void Update(){

     //shoot
     this.isShooting = (Input.GetButtonDown ("Fire1"));
 }

 
 void FixedUpdate () {

     //shoot
     if (this.isShooting) {

         this.spawnPoint = this.myTransform.Find("ProjectileSpawnPoint").position;

         //instantiate projectile at spawn point
         GameObject projectile = GameObject.Instantiate (this.projectilePrefab, this.spawnPoint, Quaternion.identity) as GameObject;

         //add force to move
         projectile.rigidbody.AddForce(this.spawnPoint * this.projectileSpeed, Force$$anonymous$$ode.Impulse);

         //kill object after delay
         Destroy(projectile, this.projectileLifeSpan);

     }

 }

[/code]

avatar image ben-tmg · Feb 27, 2014 at 06:59 PM 0
Share

So it's more of a top down shooter than a side scroller?

You do want to use a vector but you need the correct vector :)

How are you setting the facing of the character? Is it looking at a mouse pointer or are you using a joystick?

What you need to do is find a point the bullet will be going to (say a target crosshair that is controlled by a mouse) and then find the vector that goes from the player to that point. Then you need to normalize the vector so its length is 1. Then you can use it in the bullet code.

So roughly, you want:

 //The target gameObject is something you want the bullet to go towards
 var targetPoint = someGameObject.Transform.Position.
 
 //Vector from point A to point B is B - A.
 var bulletDirection = targetPoint - this.spawnPoint;
 bulletDirection.Normalize();
 
 //Fire!!!
 projectile.rigidbody.AddForce(bulletDirection * this.projectileSpeed, Force$$anonymous$$ode.Impulse)


etc.

avatar image BigRoy · Feb 27, 2014 at 09:34 PM 0
Share

You might want to use this.myTransform.forward As vector.

avatar image
0

Answer by bergerinc · Feb 28, 2014 at 01:06 AM

Okay. So based on what you suggested and also on this other example I found (http://answers.unity3d.com/questions/591383/fire-at-mouse-position-2d-game.html), here is my latest code. The player shoots at the mouse position all the time exactly as it should. So thanks for your help with that.

However, I want to target mobile devices with this game and I think it will be a lot to do to move the player up/down and left/right as well as target to shoot. I was hoping to just get the position the player was facing and tell the projectile to shoot itself in that direction. Is this something that can be done or am I completely off the reservation here?

[code]

 public GameObject prefab;
 public float projectileSpeed = 2f;
 public float projectileLifeSpan = 10f;

 private Transform myTransform;
 private Vector3 shootDirection;
 private Vector3 spawnPoint;

 private bool isShooting = false;


 void Start(){
     //set global variables
     this.myTransform = transform;
 }

 void Update(){

     //check to see if shooting
     this.isShooting = (Input.GetButtonDown ("Fire1"));
 }
 
 
 void FixedUpdate () {

     //shoot
     if (this.isShooting) {

         //get mouse position as target
         this.shootDirection = Input.mousePosition;
         this.shootDirection.z = this.myTransform.position.z - Camera.main.transform.position.z;
         this.shootDirection = Camera.main.ScreenToWorldPoint(this.shootDirection);

         //rotate
         Quaternion q = Quaternion.FromToRotation(Vector3.up, shootDirection - this.myTransform.position);

         //create projectile and fire it
         GameObject projectile = Instantiate(prefab, this.myTransform.position, q) as GameObject;
         projectile.rigidbody2D.AddForce(projectile.transform.up * 500.0f);

         //kill projectile after delay
         Destroy(projectile,this.projectileLifeSpan);
     }

 }

[/code]

Comment
Add comment · Show 2 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image ben-tmg · Feb 28, 2014 at 02:44 AM 0
Share

This is a different question :)

Use the characters 'up' axis (or which ever way it faces in local space) and convert that vector into world coordinates using transform.TransformDirection. You can use that vector ins$$anonymous$$d of the one you calculate from the shootDirection.

Also you shouldn't do the firing in FixedUpdate, that should only be used for physics related updates.

avatar image ben-tmg · Feb 28, 2014 at 03:22 AM 0
Share

You might want to look at this question

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

22 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

Collision detection for Arrows and Melee. How to properly setup physics/collision? 3 Answers

Bullet reflect not working properly 1 Answer

Increase velocity without changing trajectory 1 Answer

How do I prevent my original projectile object from being destroyed? 1 Answer

Instantiating projectile object is affecting the movement of instantiater 1 Answer


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges