Take the 2-minute tour ×
Game Development Stack Exchange is a question and answer site for professional and independent game developers. It's 100% free, no registration required.

I'm making an XNA shooter game. How do I have my sprite repeatedly shoot bullets instead of waiting for one bullet to go off the screen. Do I do this with and array?

share|improve this question
2  
What are you currently doing that prevents you from having multiple bullets right now? –  Tetrad Jan 13 '13 at 18:55
    
@Tetrad im just making the sprite move at the zombie. i know its possible what im asking i just dont know how –  Battle_Pasture Jan 13 '13 at 20:01
    
Could it be that your current code is preventing another bullet from appearing while there is a bullet on screen? –  Anko Jan 14 '13 at 0:42
add comment

2 Answers 2

up vote 1 down vote accepted

I imagine somewhere you have: Bullet bullet;

Then some methods such as:

ShootBullet(int x, int y)
{
  Bullet b = new Bullet(x, y);
}

Draw()
{
  b.Draw(SpriteBatch); //or SpriteBatch.Draw(b.tex, b.bounds, b.x, b.y)
}

Update()
{
    b.Update(); //or b.X += b.xAccel
}

Because of this, you are only allowing yourself one bullet at a time. What you want to do, since I imagine you aren't looking for the most efficient method, is to do the following.

List<Bullet> bulletsOnScreen;

In your constructor put:

bulletsOnScreen = new List<Bullet>();

Then do the following:

ShootBullet(x,y)
{
  Bullet b = new Bullet(x,y);
  bulletsOnScreen.Add(b);
}

Draw()
{
  foreach(Bullet b in bulletsOnScreen)
    b.Draw();
}

Update()
{
  foreach(Bullet b in bulletsOnScreen)
    b.Update();

  if(b.bounds.X > screen.X) //add more logic for being off screen
    bulletsOnScreen.Remove(b);
}

This will maintain a list of bullets you can keep track of, and when the bullet is no longer on screen (this is where you need to put in logic to determine if a bullet is off screen) it removes it from the list of bullets.

share|improve this answer
    
thanks helped alot –  Battle_Pasture Jan 14 '13 at 21:02
    
thank you for this, but now im having trouble getting collision detection for each one. How do i draw a new Bounding Box around each new bullet that appears on the screen? –  Battle_Pasture Jan 14 '13 at 22:00
    
Each instance of your bullet class has the same bounding box, something like 40px wide by 20 pixels high. You use the position of the bullet AND the bounding box to determine where the bounding box is in the world. Then it is a simple rectangle bounds check. Rectangle worldBound = new Rectangle(bullet.X + bullet.Bound.X, bullet.Y + bullet.Bound.Y, bullet.Bound.W, bullet.Bound.H); Thats assuming rectangles have a width/height constructor, otherwise you need to calculate the x2, y2 positions the same way I got the x1 and y1 positions. –  Olink Jan 15 '13 at 15:17
add comment

You could create a timer class, then invoke the timer so when it's finished, the timer allows the next bullet to be shot.

I'm pretty sure this would work Create a separate class named Timer and put this in it.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;

namespace (your namespace) {
class Timer
    {
        int TimeToDelay;
        int TimeElapsed;
        public bool IsTimerDone;

        public void StartTimer(GameTime gt, int AmountOfTime)
        {
            while (AmountOfTime < TimeElapsed)
            {
                IsTimerDone = false;
                TimeToDelay = AmountOfTime;
                if (IsTimerDone == false)
                {
                    if (TimeToDelay == gt.ElapsedGameTime.TotalSeconds)
                    {
                        IsTimerDone = true;

                    }
                    else TimeElapsed += 1;
                }
            }
        }
    }
}

Then Invoke the timer class in the main game class.

namespace (GameNameHere)
{
    /// <summary>
    /// This is the main type for your game
    /// </summary>
    public class Game1 : Microsoft.Xna.Framework.Game
    {
        GraphicsDeviceManager graphics;
        SpriteBatch spriteBatch;

        public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
        }

        /* DECLARE INIT VARIABLES */
    // Declare Timer
        Timer timer;
    Bool BulletReady = true;    

        protected override void Initialize()
        {
            /* Init logic */

        // Create New Instance of The Timer     
        timer = new Timer();        

            base.Initialize();
        }

        protected override void LoadContent()
        {
            // Create a new SpriteBatch, which can be used to draw textures.
            spriteBatch = new SpriteBatch(GraphicsDevice);


        }

        protected override void UnloadContent()
        {
            // TODO: Unload any non ContentManager content here
        }


        protected override void Update(GameTime gameTime)
        {
            // Allows the game to exit
            if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
                this.Exit();

            // REPLACE CONTROL CODE WITH INVOKE/BUTTONPRESS HERE
            // if (GamePad.GetState(PlayerIndex.One).Buttons.A == ButtonState.Pressed)
            // {
                if (BulletReady == true)
                {
                    if (timer.IsTimerDone == false)
                    {
                        // replace 1 with amount of time (in seconds)
                        timer.StartTimer(gameTime, 1);
                        BulletReady = false;
                    }
                    else if (timer.IsTimerDone == true)
                    {
                        BulletReady = true;
                    }

                }

                }
            // }


            // TODO: Add your update logic here

            base.Update(gameTime);
        }


        protected override void Draw(GameTime gameTime)
        {
            GraphicsDevice.Clear(Color.CornflowerBlue);

            // TODO: Add your drawing code here

            base.Draw(gameTime);
        }
    }
}

The bulletready boolean value is for so you can shoot again. If it is true, You can shoot, vice versa.

Basically, for the invoke, Create the timer's variable, Create a new instance in the initialization, Then in update, check for gamepad input, and if the bulletready is true, start a timer for the amount of time you want the bullet to be on cool down.

share|improve this answer
    
thanks, i have no trouble with the timing of the bullets its just getting a second bullet on the screen at any given time. –  Battle_Pasture Jan 13 '13 at 21:59
    
Unless the student knows OOP, encapsulating the timer in a class is likely a bit overkill for someone having trouble implementing a timer for the first time in their lives. –  Anko Jan 14 '13 at 0:35
    
@Anko No its not the timer im having trouble with, its actually having a second bullet on the screen at any given time. –  Battle_Pasture Jan 14 '13 at 1:09
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.