Search Unity

Help with moving a spaceship in 2d project

Discussion in '2D' started by fosmark13, Feb 16, 2016.

  1. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    Hi i'm currently doing a spaceship with a gun that throws "rays" from it but i'm having problems trying to make it work, currently the spaceship can move from point A to point B and it shoots to, the spaceship can shoot in 3 directions depending on where the player is (i check this whit a collider that sends one bool), the problem here is that the spaceship shoots correctly when is not moving... but when i put some moveSpeed to it the shoot points start to auto increase so if it moves to the left the "rays" start to go more to the left even if the player moves to the others colliders, that happens if i do it with this method:

    Code (CSharp):
    1.  
    2.  
    3. spaceRayClone = Instantiate (spaceRay, shootPoint1.transform.position, shootPoint1.transform.rotation) as GameObject;
    4.  
    5.                      Vector2 direction = shootPointDirection1.transform.position - transform.position;
    6.  
    7.                     direction.Normalize ();
    8.  
    9.                     spaceRayClone.GetComponent<Rigidbody2D> ().velocity = direction * raySpeed;
    10.  
    11.                     Destroy (spaceRayClone, 2f);
    12.  
    it works well but only when is without velocity.

    I tried moveTowards too using this method:

    Code (CSharp):
    1.  
    2.  
    3. spaceRayClone = Instantiate (spaceRay, shootPoint1.transform.position, shootPoint1.transform.rotation) as GameObject;
    4.  
    5.                        Vector3 directionPoint1 = shootPointDirection1.transform.position;
    6.  
    7.                         spaceRayClone.transform.position = Vector3.MoveTowards(shootPoint1.transform.position,directionPoint1, raySpeed * Time.deltaTime);
    8.  
    9.  
    10.                         Destroy (spaceRayClone, 2f);
    11.  

    i have it in my Update section but the Clones never move, it only create them but they are not moving, so neither of both methods is fully functional, the first works but when is not moving and the second does not even do the "ray" movement, so any idea i've been trying to do this for days but it's just not working!!!!

    note: I check at the inspector and everything is placed correctly, it even shows at what point the "rays" are going.


    this is how i move the spaceship:

    Code (CSharp):
    1. spaceShip.transform.position = Vector3.MoveTowards(spaceShip.transform.position, currentPoint.position, Time.deltaTime * moveSpeed);
    2.  
    3.         if (spaceShip.transform.position == currentPoint.position) {
    4.  
    5.             pointSelection++;
    6.  
    7.             GetComponentInChildren<SpriteRenderer> ().flipX = false;
    8.  
    9.             if(pointSelection == points.Length){
    10.  
    11.                 pointSelection =0;
    12.  
    13.                 GetComponentInChildren<SpriteRenderer> ().flipX = true;
    14.  
    15.  
    16.             }
    17.  
    18.             currentPoint = points [pointSelection];
    19.  
    20.         }
     
  2. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Since you're using physics to move things, try using Rigidbody2D.Addforce to change your object's velocity instead of setting position or directly setting velocity. First parameter is your direction * force, second parameter would be ForceMode2D.Impulse.

    To be honest I had trouble following your explanation of the problem, but maybe that will help you.
     
  3. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91

    hi thanks for your advice but i tried that to, here's the code:

    Code (CSharp):
    1. Vector2 direction = shootPointDirection1.transform.position - transform.position;
    2.  
    3.                         direction.Normalize ();
    4.  
    5.                         spaceRayClone = Instantiate (spaceRay, shootPoint1.transform.position, shootPoint1.transform.rotation) as GameObject;
    6.  
    7.                         spaceRayClone.GetComponent<Rigidbody2D> ().AddForce (direction * rayForce, ForceMode2D.Impulse);
    and works to... the problem is when i assign a moveSpeed to my object(the sapceship) instead of keeping the trajectory of the "rays" it starts to throw them away to the direction point. i made this draw if it can explain it better.

    the RED lines are the trajectory of de "rays"once the spaceship has movement, why is that??

    thanks for your reply!!! 1.jpg
     
  4. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Does your gun always point towards the target?

    Using your diagram point labels:

    If the X axis of Point1 is always pointed towards Point2, you can do this:
    Code (CSharp):
    1. GameObject ray = Instantiate(rayPrefab, Point1.position, Point1.rotation);
    2. ray.GetComponent<Rigidbody2D>().AddForce(Point1.right, rayForce, ForceMode2D.Impulse);
    If the X axis of Point1 isn't always pointed at Point2, but the ray should always go towards Point2, you can do this:
    Code (CSharp):
    1.  
    2. // direction from Point1 to Point2
    3. Vector2 direction = (Point2.position - Point1.position).normalized;
    4. // the angle of that direction
    5. float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
    6.  
    7. // make the gameobject at Point1's position, and give it a rotation on the Z axis of the direction angle
    8. GameObject ray = Instantiate(rayPrefab, Point1.position, Quaternion.AngleAxis(angle, Vector3.forward));
    9. // add a force in the direction
    10. ray.GetComponent<Rigidbody2D>().AddForce(direction, rayForce, ForceMode2D.Impulse);
     
    fosmark13 likes this.
  5. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91


    Hi again i tried both of them and the second works better than the others that i have, the gun is flying and when the player touches the collider it triggers to shoot him from Point1 to Point2 and the Point1 is always pointing towards Point2, again this works perfectly when the spaceship is not moving, but when i add some moveSpeed to the spaceship, it starts to shoot a little backward... lets say for example... if my player enters from left to right and the spaceship is moving to the left (like the draw) the "rays" are shot a little to the right of Point2 and when the spaceship goes back to the right the "rays" are shot a little to the left, i was supposing that they are being affected by some other forces because this doesn't happen when the spaceship is without move, the prefab has a Rigibody2D but is without gravity, so i think is the movement of the spaceship what is affecting the straight line of the "rays".

    is there a way that the line keeps perfect and not affected by the trajectory of the spaceship?

    Thanks for your help i really appreciate it
     
  6. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    The raycast shouldn't be affected by the ship's movement.

    If you feel comfortable sharing a more complete version of your functions, I might be able to help you out better. It's hard for me to know what the problem could be just from the description.
     
    fosmark13 likes this.
  7. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    not at all, this is my code:

    Code (CSharp):
    1.  
    2.  
    3.  
    4.     public float shootInterval;
    5.  
    6.     public float raySpeed;
    7.  
    8.      public float raysTimer;
    9.  
    10.     public int cloneCount;
    11.  
    12.     public int numberOfRays;
    13.  
    14.     public float timeForNextClones;
    15.  
    16.     public float cloneTime;
    17.  
    18.  
    19.  
    20.     public bool lookingRight = false;
    21.  
    22.     public bool attack;
    23.  
    24.  
    25.  
    26.     public bool usingLeft = false;
    27.  
    28.     public bool usingMiddle = false;
    29.  
    30.     public bool usingRight = false;
    31.  
    32.  
    33.  
    34.  
    35.     public GameObject spaceRay;
    36.  
    37.  
    38.     private Animator animSpaceshipGunner;
    39.  
    40.  
    41.     public float rayForce;
    42.        
    43.     public Transform shootPoint1;
    44.  
    45.     public Transform shootPointDirection1;
    46.  
    47.  
    48.  
    49.  
    50.     public Transform shootPoint2;
    51.  
    52.     public Transform shootPointDirection2;
    53.  
    54.  
    55.     public Transform shootPoint3;
    56.  
    57.     public Transform shootPointDirection3;
    58.  
    59.  
    60.     public Transform currentShootingPoint;
    61.  
    62.     public Vector2 realCurrentDirection;
    63.  
    64.  
    65.  
    66.     public GameObject spaceShip;
    67.  
    68.     public GameObject spaceRayClone;
    69.  
    70.  
    71.     public float moveSpeed;
    72.  
    73.     public Transform currentPoint;
    74.  
    75.     public Transform[] points;
    76.  
    77.     public int pointSelection;
    78.  
    79.     public bool noMoreClones = false;
    80.  
    81.  
    82.  
    83.  
    84.     private spaceshipGunnerAttackLeft ssgAL;
    85.  
    86.  
    87.     // Use this for initialization
    88.     void Start () {
    89.  
    90.         currentPoint = points [pointSelection];
    91.  
    92.         animSpaceshipGunner = gameObject.GetComponent<Animator>();
    93.  
    94.  
    95.  
    96.     }
    97.  
    98.  
    99.     // Update is called once per frame
    100.  
    101.     void Update () {
    102.  
    103.         if(!usingLeft && !usingMiddle && !usingRight){
    104.  
    105.  
    106.             cloneCount = 0;
    107.  
    108.             noMoreClones = false;
    109.  
    110.             timeForNextClones = 0;
    111.  
    112.             currentShootingPoint = null;
    113.  
    114.             raysTimer = 0;
    115.  
    116.         }
    117.  
    118.  
    119.  
    120.  
    121.     }
    122.  
    123.     void FixedUpdate (){
    124.  
    125.  
    126.         spaceShip.transform.position = Vector3.MoveTowards(spaceShip.transform.position, currentPoint.position, Time.deltaTime * moveSpeed);
    127.  
    128.         if (spaceShip.transform.position == currentPoint.position) {
    129.  
    130.             pointSelection++;
    131.  
    132.             GetComponentInChildren<SpriteRenderer> ().flipX = false;
    133.  
    134.             if(pointSelection == points.Length){
    135.  
    136.                 pointSelection =0;
    137.  
    138.                 GetComponentInChildren<SpriteRenderer> ().flipX = true;
    139.  
    140.  
    141.             }
    142.  
    143.             currentPoint = points [pointSelection];
    144.  
    145.         }
    146.  
    147.  
    148.         if (usingLeft) {
    149.  
    150.             usingMiddle = false;
    151.  
    152.             usingRight = false;
    153.  
    154.  
    155.             raysTimer += Time.deltaTime;
    156.  
    157.             if (raysTimer >= shootInterval) {
    158.  
    159.  
    160.                 if (!noMoreClones && !usingMiddle && !usingRight) {
    161.  
    162.  
    163.                     GetComponent<AudioSource> ().Play ();
    164.  
    165.                     cloneCount++;
    166.  
    167.  
    168.  
    169.                     if (cloneCount <= numberOfRays) {
    170.  
    171.                         Vector2 direction = (shootPointDirection1.transform.position - shootPoint1.position).normalized;
    172.  
    173.                         //direction.Normalize ();
    174.  
    175.                         float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
    176.  
    177.                         spaceRayClone = Instantiate (spaceRay, shootPoint1.position, Quaternion.AngleAxis(angle, Vector3.forward)) as GameObject;
    178.  
    179.                         spaceRayClone.GetComponent<Rigidbody2D>().AddForce(direction * rayForce, ForceMode2D.Impulse);
    180.  
    181.                         //spaceRayClone.GetComponent<Rigidbody2D> ().AddForce (shootPoint1.right, ForceMode2D.Impulse);
    182.  
    183.                         //    Vector3 directionPoint1 = shootPointDirection1.transform.position;
    184.  
    185.                         //spaceRayClone.transform.position = Vector3.MoveTowards(shootPoint1.transform.position,directionPoint1, raySpeed * Time.deltaTime);
    186.  
    187.  
    188.  
    189.                         //spaceRayClone.transform.position = Vector3.MoveTowards (shootPoint1.position, shootPointDirection1.transform.position, raySpeed * Time.deltaTime);
    190.  
    191.                         //spaceRayClone.GetComponent<Rigidbody2D> ().velocity = direction * raySpeed;
    192.  
    193.                         currentShootingPoint = shootPointDirection1;
    194.  
    195.                         raysTimer = 0;
    196.  
    197.                         Destroy (spaceRayClone, 2f);
    198.  
    199.  
    200.  
    201.  
    202.  
    203.                     } else if (cloneCount > numberOfRays) {
    204.  
    205.                         noMoreClones = true;
    206.  
    207.  
    208.                     }
    209.  
    210.  
    211.                 }
    212.  
    213.             }
    214.  
    215.  
    216.         }
    217.  
    218.  
    219.  
    220.  
    221.         if(usingMiddle){
    222.  
    223.             usingLeft = false;
    224.  
    225.             usingRight = false;
    226.  
    227.             raysTimer += Time.deltaTime;
    228.  
    229.             if (raysTimer >= shootInterval) {
    230.  
    231.  
    232.                 if (!noMoreClones && !usingLeft && !usingRight) {
    233.  
    234.  
    235.  
    236.                     GetComponent<AudioSource> ().Play ();
    237.  
    238.                     cloneCount++;
    239.  
    240.  
    241.  
    242.                     if(cloneCount <= numberOfRays){
    243.  
    244.  
    245.                         Vector2 direction = (shootPointDirection2.transform.position - shootPoint2.position).normalized;
    246.  
    247.                         float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
    248.  
    249.                         spaceRayClone = Instantiate (spaceRay, shootPoint2.position, Quaternion.AngleAxis(angle, Vector3.forward)) as GameObject;
    250.  
    251.                         spaceRayClone.GetComponent<Rigidbody2D>().AddForce(direction * rayForce, ForceMode2D.Impulse);
    252.  
    253.  
    254.  
    255.                         currentShootingPoint = shootPointDirection2;
    256.  
    257.                         raysTimer = 0;
    258.  
    259.                         Destroy (spaceRayClone, 2f);
    260.  
    261.  
    262.                     }else if(cloneCount > numberOfRays){
    263.  
    264.                         noMoreClones = true;
    265.  
    266.  
    267.                     }
    268.  
    269.  
    270.  
    271.                 }
    272.  
    273.             }
    274.  
    275.         }
    276.  
    277.         if(usingRight){
    278.  
    279.             usingLeft = false;
    280.  
    281.             usingMiddle = false;
    282.  
    283.             raysTimer += Time.deltaTime;
    284.  
    285.             if (raysTimer >= shootInterval) {
    286.  
    287.  
    288.                 if (!noMoreClones && !usingLeft && !usingMiddle) {
    289.  
    290.                
    291.  
    292.                     GetComponent<AudioSource> ().Play ();
    293.  
    294.                     cloneCount++;
    295.  
    296.  
    297.  
    298.                     if(cloneCount <= numberOfRays){
    299.  
    300.                         Vector2 direction = (shootPointDirection3.transform.position - shootPoint3.position).normalized;
    301.  
    302.                         float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
    303.  
    304.                         spaceRayClone = Instantiate (spaceRay, shootPoint3.position, Quaternion.AngleAxis(angle, Vector3.forward)) as GameObject;
    305.  
    306.                         spaceRayClone.GetComponent<Rigidbody2D>().AddForce(direction * rayForce, ForceMode2D.Impulse);
    307.  
    308.  
    309.                         currentShootingPoint = shootPointDirection3;
    310.  
    311.                         raysTimer = 0;
    312.  
    313.                         Destroy (spaceRayClone, 2f);
    314.  
    315.                     }else if(cloneCount > numberOfRays){
    316.  
    317.                         noMoreClones = true;
    318.  
    319.  
    320.                     }
    321.  
    322.  
    323.  
    324.                 }
    325.  
    326.             }
    327.  
    328.  
    329.         }
    330.  
    331.  
    332.         if(noMoreClones){
    333.  
    334.             timeForNextClones += Time.deltaTime;
    335.  
    336.             if(timeForNextClones >= cloneTime){
    337.  
    338.                 cloneCount = 0;
    339.  
    340.                 noMoreClones = false;
    341.  
    342.                 timeForNextClones = 0;
    343.  
    344.  
    345.                 usingLeft = false;
    346.  
    347.                 usingMiddle = false;
    348.  
    349.                 usingRight = false;
    350.  
    351.                 currentShootingPoint = null;
    352.  
    353.        
    354.  
    355.  
    356.             }
    357.  
    358.         }
    359.  
    360.  
    This is the code for my spaceship (above) and like i said before it shoots from 3 different "shootPoints" to 3 different "shootDirections" which are left, middle and right, this is determined with a bool that indicates what collider is trigger (usingLeft, usingMiddle and usingRight) and noMoreClones is just for keeping a wave of 3 constant "rays" a pause and the continue.

    this is the code of the Collider:

    Code (CSharp):
    1.  
    2.  
    3.     private spaceshipGunnerAI ssgAI;
    4.  
    5.  
    6.     // Use this for initialization
    7.     void Start () {
    8.  
    9.         ssgAI = GetComponentInParent<spaceshipGunnerAI> ();
    10.  
    11.     }
    12.  
    13.     void OnTriggerStay2D(Collider2D col){
    14.  
    15.         if (col.CompareTag ("Player")) {
    16.  
    17.             ssgAI.usingLeft = true;
    18.         }
    19.  
    20.  
    21.     }
    22.        
    23.        
    24. }
    25.  
    like this are other 2 wich are the usingMiddle and usingRight but they are basically the same.
    thanks for the help!!!
     
  8. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Hey, I hope you don't mind, but I've taken the liberty of cleaning up your code.

    There seems to be a lot going on in the SpaceShipGunnerAI class, so hopefully I didn't break anything. This should do the same thing as your current code, but is easier to read and debug.

    Instead of using three booleans for left, middle, and right, I replaced them with an Enum "DetectionZone". An enum is a nice way to define a list of options. Making a public enum-type variable will show a dropdown menu in the inspector, which is what I did for the collider class to choose which zone it represents.

    Let me know if you have trouble following anything I've done here. I really just broke up your code into more functions.

    I haven't tested this, so hopefully it doesn't cause you any problems. If you decide to use this directly, make sure to backup your old stuff just in case.

    Code (CSharp):
    1. public class SpaceShipGunnerAI : MonoBehaviour {
    2.     public enum DetectionZone {
    3.         none,
    4.         left,
    5.         middle,
    6.         right,
    7.     }
    8.  
    9.     public GameObject spaceRay;
    10.     public float rayForce;
    11.     public float shootInterval;
    12.     public int cloneCount;
    13.     public int numberOfRays;
    14.     public float cloneTime;
    15.     public float moveSpeed;
    16.  
    17.     public Transform shootPoint1;
    18.     public Transform shootPointDirection1;
    19.  
    20.     public Transform shootPoint2;
    21.     public Transform shootPointDirection2;
    22.  
    23.     public Transform shootPoint3;
    24.     public Transform shootPointDirection3;
    25.  
    26.     public Transform currentShootingPoint;
    27.     public Vector2 realCurrentDirection;
    28.  
    29.     public GameObject spaceShip;
    30.  
    31.     public Transform currentPoint;
    32.     public Transform[] points;
    33.     public int pointSelection;
    34.    
    35.     // this is a property, behaves like a normal variable
    36.     // but can do more when you try to get the value or set the value
    37.     // this one just acts like a normal public variable, but isn't shown in the inspector.
    38.     public DetectionZone CurrentZone { get; set; }
    39.  
    40.     private bool noMoreClones;
    41.     private float raysTimer;
    42.     private float cloneTimer;
    43.     private bool lookingRight = false;
    44.     private Animator animSpaceshipGunner;
    45.     private SpriteRenderer spriteRenderer;
    46.     private AudioSource audioSource;
    47.  
    48.     private void Start() {
    49.         currentPoint = points[pointSelection];
    50.         animSpaceshipGunner = gameObject.GetComponent<Animator>();
    51.         spriteRenderer = GetComponentInChildren<SpriteRenderer>();
    52.         audioSource = GetComponent<AudioSource>();
    53.     }
    54.  
    55.     private void Update() {
    56.         if(CurrentZone == DetectionZone.none) {
    57.             ResetCloneTimer();
    58.             ResetRaysTimer();
    59.         }
    60.     }
    61.  
    62.     void FixedUpdate() {
    63.         UpdateMovement();
    64.  
    65.         raysTimer += Time.deltaTime;
    66.         if(raysTimer >= shootInterval) {
    67.             switch(CurrentZone) {
    68.                 case DetectionZone.left:
    69.                     ShootRay(shootPoint1.position, shootPointDirection1.position);
    70.                     break;
    71.                 case DetectionZone.middle:
    72.                     ShootRay(shootPoint2.position, shootPointDirection2.position);
    73.                     break;
    74.                 case DetectionZone.right:
    75.                     ShootRay(shootPoint3.position, shootPointDirection3.position);
    76.                     break;
    77.             }
    78.         }
    79.  
    80.         UpdateClones();
    81.     }
    82.  
    83.     private void UpdateMovement() {
    84.         spaceShip.transform.position = Vector3.MoveTowards(spaceShip.transform.position, currentPoint.position, Time.deltaTime * moveSpeed);
    85.         if(spaceShip.transform.position == currentPoint.position) {
    86.             pointSelection++;
    87.             spriteRenderer.flipX = false;
    88.             if(pointSelection == points.Length) {
    89.                 pointSelection = 0;
    90.                 spriteRenderer.flipX = true;
    91.             }
    92.             currentPoint = points[pointSelection];
    93.         }
    94.     }
    95.  
    96.     private void ShootRay(Vector3 origin, Vector3 target) {
    97.         if(!noMoreClones) {
    98.             if(cloneCount <= numberOfRays) {
    99.                 audioSource.Play();
    100.                 cloneCount++;
    101.                 Vector2 direction = (target - origin).normalized;
    102.                 float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
    103.  
    104.                 GameObject spaceRayClone = Instantiate(spaceRay, origin, Quaternion.AngleAxis(angle, Vector3.forward)) as GameObject;
    105.                 Rigidbody2D body = spaceRayClone.GetComponent<Rigidbody2D>();
    106.                 if(body != null) {
    107.                     body.AddForce(direction * rayForce, ForceMode2D.Impulse);
    108.                 }
    109.                 ResetRaysTimer();
    110.                 Destroy(spaceRayClone, 2f);
    111.             } else {
    112.                 noMoreClones = true;
    113.             }
    114.         }
    115.     }
    116.  
    117.     private void UpdateClones() {
    118.         if(noMoreClones) {
    119.             cloneTimer += Time.deltaTime;
    120.             if(cloneTimer >= cloneTime) {
    121.                 ResetCloneTimer();
    122.             }
    123.         }
    124.     }
    125.  
    126.     private void ResetRaysTimer() {
    127.         raysTimer = 0;
    128.     }
    129.  
    130.     private void ResetCloneTimer() {
    131.         cloneCount = 0;
    132.         noMoreClones = false;
    133.         cloneTimer = 0;
    134.         CurrentZone = DetectionZone.none;
    135.     }
    136. }

    and then the collider object class:
    Code (CSharp):
    1. public class SpaceShipZone : MonoBehaviour
    2. {
    3.     // assigned in inspector
    4.     public SpaceShipGunnerAI.DetectionZone zone;
    5.     private SpaceShipGunnerAI ssgAI;
    6.  
    7.     private void Start() {
    8.         ssgAI = GetComponentInParent<SpaceShipGunnerAI>();
    9.     }
    10.  
    11.     private void OnTriggerStay2D(Collider2D collider) {
    12.         if(collider.CompareTag("Player")) {
    13.             ssgAI.CurrentZone = zone;
    14.         }
    15.     }
    16. }
     
    Last edited: Feb 18, 2016
  9. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    \


    Hi thanks again for your answer and don't worry for the code is cool that way too, so i've been testing this today and it currently works great but again just like the previous method once the velocity is defined the "rays" start to shoot a little behind the direction point depending on the spaceship's direction, i recorded it and here's the link:



    there you can appreciate that the spaceship shoots correctly when is not moving but once i put moveSpeed to 1 the rays start to be a few millimeters behind the direction they should be.

    Thanks you're great i'll be watching
     
  10. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Hey there, I'm glad you took the time to make the video, it should be very insightful to where the problem lies.

    However your video seems to be set to Private currently.
     
  11. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    Sorry it's public now
     
    LiterallyJeff likes this.
  12. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    I think I understand now.

    There's actually no problem at all, the code is working perfectly as written.

    What's happening is that the projectiles are being created, and traveling towards a position. Then the ship moves, and it appears like the bullet is going crooked, but really it just continued on it's starting path from the moment it spawned, unaffected by the ship's movement.

    I think what you're looking for is the bullets to move with the ship as it moves, if that's the case, then the bullets can't realistically use physics, because their position has to be affected by things other than the physics engine.

    So what you can do is add a script to your projectile prefab like this:

    Code (CSharp):
    1.  
    2. public class BulletBehavior : MonoBehaviour {
    3.     public float speed;
    4.     public Space movementRelativeTo;
    5.  
    6.     private void Update() {
    7.         transform.Translate(Vector3.right * speed * Time.deltaTime, movementRelativeTo);
    8.     }
    9. }
    Then change your ShootRay function to this:
    Code (CSharp):
    1. private void ShootRay(Vector3 origin, Vector3 target) {
    2.         if(!noMoreClones) {
    3.             if(cloneCount <= numberOfRays) {
    4.                 audioSource.Play();
    5.                 cloneCount++;
    6.  
    7.                 Vector2 direction = (target - origin).normalized;
    8.                 float angle = Mathf.Atan2(direction.y, direction.x) * Mathf.Rad2Deg;
    9.  
    10.                 GameObject spaceRayClone = Instantiate(spaceRay, origin, Quaternion.AngleAxis(angle, Vector3.forward)) as GameObject;
    11.                 spaceRayClone.transform.SetParent(transform);
    12.  
    13.                 ResetRaysTimer();
    14.                 Destroy(spaceRayClone, 2f);
    15.             } else {
    16.                 noMoreClones = true;
    17.             }
    18.         }
    19.     }

    So you'll have to setup your projectile prefab's speed, and set "movementRelativeTo" to "Self".

    What this does is put the movement logic on the bullet, not using Rigidbody2D for movement, and tells the bullet to move towards its own X axis, going "speed" units per second. When the projectiles are spawned, they're already facing the target, so they should already be pointed in the correct direction for movement.

    Then the bullet is parented to the ship in the ShootRay function, and will move along with the ship while also going it's own direction.

    Set the bullet's Rigidbody2D to Kinematic, so that physics doesn't drive the movement, but you can still get physics collision detection.
     
  13. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    i understand what you've said and already implement the changes to the code and make a different prefab with the specifications and the new script, now what it does is that every time it shoots the sprite is not showing and when i put some speed to the spaceship, it does the same... now appears the trajectory of the bullets but when i put the speed on it i can see that the trajectory is wrong again.

    this is my hierarchy for the spaceship maybe something is wrong there

    SpaceshipGunner (this has the SpaceShipGunnerAI Script)
    ----spaceship (this has only the spriteRender of the spaceShip)
    ---------- spaceshipCollider (only a circleCollider2D)
    -----------colliderLeft (a polygonCollider with the spaceShipZone Script)
    -----------colliderMiddle (the same as above)
    -----------colliderRight (the same as above)
    -----------shootingPoint1 (just a GameObject)
    -----------shootingDirection1 (just a GameObject)
    -----------shootingPoint2 (just a GameObject)
    -----------shootingDirection2 (just a GameObject)
    -----------shootingPoint3 (just a GameObject)
    -----------shootingDirection3 (just a GameObject)
    ----startPoint
    ----endPoint

    EDIT: these are the pictures


    Captura de pantalla 2016-02-19 a las 7.40.37 p.m..png Captura de pantalla 2016-02-19 a las 7.40.15 p.m..png Captura de pantalla 2016-02-19 a las 7.39.55 p.m..png

    the third where is a weird collider is the instantiated object, it's super small
    Thanks again you're awesome!!
     
    Last edited: Feb 20, 2016
  14. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Hey there,

    When your projectiles are instantiated, make sure they're becoming children of the SpaceShipGunner properly. Your bullet appears to be set up correctly. Double check that when you drag out a spaceRay prefab, it looks correct in the scene.

    Try pausing the game when the bullets are flying, and check their settings. Why might they not be visible? Are their scales messed up? Sorting order correct? Are they in the correct positions?

    As long as the bullet has the ship as the parent, it should follow the parent wherever it moves. Then with the BulletBehavior script, the bullet should move along it's trajectory in addition to the ship's motion.
     
    fosmark13 likes this.
  15. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    hi sorry for the late, i checked what you say and the bullets are not being children of the spaceShip itself, they are children of the prefab (called spaceshipGunner) but not of the spaceShip where is the script and everything else. Captura de pantalla 2016-02-24 a las 9.35.47 a.m..png

    do you believe this is the error?? Thanks


    EDIT: i solved (thanks to you!!) i had the script in the first spaceShipGunner object, i just moved it to the spaceShip that has all the children and works exactly as i wanted!! , but i noticed that the sprites don't show up 'cause of this line of code:

    Code (CSharp):
    1. spaceRayClone.transform.SetParent(transform);
    if i delete it, the sprites show again but with the wrong movement of course, is there something wrong?? now the movement is correct but the sprites don't show up, i checked the bullets when is in play mode but they are correctly in their aspects so i don't know why is that line of code affecting the sprites
     
    Last edited: Feb 24, 2016
  16. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Hey, good job experimenting and finding a solution. Another solution (if that one doesn't work for some reason), would be to keep the script where it was, and since the script has a reference to the actual moving spaceship, you can do this instead:
    Code (CSharp):
    1. spaceRayClone.transform.SetParent(spaceShip.transform);
    When you play the game and the sprites don't appear, can you see the gameobjects in the scene view? Does the Z value get messed up or anything? Make sure you check in 3D view just in case the bullets get strangely rotated or something.
     
  17. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    Hi again when i'm playing the game the GameObjects appear in the hierarchy and i can see them because of an icon that i put to them, but when i select them everything seems to be correct even if i select the 3D view the only thing that appears is a box but there's no sprite anywhere, the only thing that is changing is its rotation on Z from 0 goes to 217 but when i return it to cero nothing happens.. is this the problem?? the rotation??
     
  18. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Hm, that's strange. Make sure the scale is set correctly, and the sorting order. Z having rotation is expected, X or Y rotation would cause problems. Make sure the SpriteRenderer color isn't set to alpha 0 or anything.

    If you want me to take a look at your project and see whats wrong you can private message me with a download link, but without seeing more it's difficult to figure out what could be wrong.
     
  19. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    Hi ok so here's the spaceship project
     

    Attached Files:

  20. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Hey, I'll have to wait until I'm home tonight to open that, but I will check it out and get back to you.
     
  21. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    Looks like your projectiles have a scale of 0.

    Add this line after the SetParent in ShootRay:
    Code (CSharp):
    1. spaceRayClone.transform.localScale = Vector3.one;
     
  22. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91

    man i can´t believe i didn't see that, but you´re right, now the spaceship does the movement correct as well as the shooting, you are very talented, is there a way that i can help you with something or some kind of support for you?? maybe you can give me more help with some of my game functions and work together through email?? if you pass me your email we can reach an arrangement or something?? thanks a lot and i´ll be waiting for your answer
     
  23. LiterallyJeff

    LiterallyJeff

    Joined:
    Jan 21, 2015
    Posts:
    2,807
    lol thanks, it's really no problem. If you need more help you're better off posting your questions in these forums or on the answerhub first, because I'm only on here in my free time. There's plenty of talented developers here to help you.
     
  24. fosmark13

    fosmark13

    Joined:
    Feb 16, 2015
    Posts:
    91
    alright then, thanks for your help you're awesome