using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;
namespace WindowsGame3
{
public class Game1 : Microsoft.Xna.Framework.Game
{
GraphicsDeviceManager graphics;
SpriteBatch spriteBatch;
Texture2D ship, bullet, alien;
Texture2D[] aliens = new Texture2D[20];
Texture2D[] bullets = new Texture2D[10];
Vector2 shipPos = new Vector2(200, 540);
Vector2 alienPos = new Vector2(200, 400);
Vector2 bulletPos = new Vector2(200, 450);
Vector2[] aliensPos = new Vector2[20];
Vector2[] bulletsPos = new Vector2[10];
int alienCount = 0;
int bulletCount = 0;
KeyboardState state = Keyboard.GetState();
public Game1()
{
graphics = new GraphicsDeviceManager(this);
Content.RootDirectory = "Content";
graphics.PreferredBackBufferWidth = 400;
graphics.PreferredBackBufferHeight = 600;
}
protected override void Initialize()
{
base.Initialize();
}
protected override void LoadContent()
{
spriteBatch = new SpriteBatch(GraphicsDevice);
alien = Content.Load<Texture2D>("alien");
ship = Content.Load<Texture2D>("ship");
for (int x = 0; x < 5; x++)
{
for (int y = 0; y < 4; y++)
{
aliens[alienCount] = Content.Load<Texture2D>("alien");
aliensPos[alienCount].X = 100 + (x * 40);
aliensPos[alienCount].Y = 20 + (y * 40);
alienCount++;
}
}
}
protected override void UnloadContent()
{
}
protected override void Update(GameTime gameTime)
{
if (state.IsKeyDown(Keys.Right) && shipPos.X < 360)
{
shipPos.X += 5;
}
if (state.IsKeyDown(Keys.Left) && shipPos.X > 0)
{
shipPos.X -= 5;
}
if (state.IsKeyDown(Keys.Space))
{
bullets[bulletCount] = Content.Load<Texture2D>("bullet");
bulletsPos[bulletCount].X = shipPos.X;
bulletsPos[bulletCount].Y = shipPos.Y;
bulletCount++;
}
base.Update(gameTime);
}
protected override void Draw(GameTime gameTime)
{
GraphicsDevice.Clear(Color.Black);
spriteBatch.Begin(SpriteSortMode.BackToFront, BlendState.AlphaBlend);
spriteBatch.Draw(ship, shipPos, Color.White);
spriteBatch.Draw(alien, alienPos, Color.White);
for (int alienCount = 0; alienCount < 20; alienCount++)
{
spriteBatch.Draw(aliens[alienCount], aliensPos[alienCount], Color.White);
}
for (int bulletCount = 0; bulletCount < 10; bulletCount++)
{
spriteBatch.Draw(bullets[bulletCount], bulletsPos[bulletCount], Color.White);
}
spriteBatch.End();
base.Draw(gameTime);
}
}
}
我想在船只位置创建一个子弹并将该子弹存储在一个数组中,但是当我从数组中绘制子弹时,我的绘制方法中我得到错误消息此方法不接受此参数的null。 参数名称:texture
答案 0 :(得分:3)
在XNA中,最好在需要之前加载所有资源,这就是你拥有的LoadContent()方法。您应该在那里加载项目符号纹理,然后在必要时在Update()中使用它。
每个图像只需要一个Texture2D对象,即使您想要多次绘制它也是如此。 你不需要Texture2D数组充满了相同的图像。
所以,举个例子:
protected override void LoadContent()
{
spriteBatch = new SpriteBatch(GraphicsDevice);
alien = Content.Load<Texture2D>("alien"); //only one texture needed
ship = Content.Load<Texture2D>("ship");
bullet = Content.Load<Texture2D>("bullet"); //only one texture needed
//set initial positions as before
for (int x = 0; x < 5; x++)
{
for (int y = 0; y < 4; y++)
{
aliensPos[alienCount].X = 100 + (x * 40);
aliensPos[alienCount].Y = 20 + (y * 40);
alienCount++;
}
}
}
当你想制作新的外星人或子弹时,你只需设置他们的位置,因为图像已经加载:
if (state.IsKeyDown(Keys.Space))
{
bulletsPos[bulletCount].X = shipPos.X;
bulletsPos[bulletCount].Y = shipPos.Y;
bulletCount++;
}
然后,当你已经加载并准备好所有纹理时,你可以绘制它:
protected override void Draw(GameTime gameTime)
{
GraphicsDevice.Clear(Color.Black);
spriteBatch.Begin(SpriteSortMode.BackToFront, BlendState.AlphaBlend);
spriteBatch.Draw(ship, shipPos, Color.White);
for (int alienCount = 0; alienCount < 20; alienCount++)
{
//draw alien texture for every aliensPos
spriteBatch.Draw(alien, aliensPos[alienCount], Color.White);
}
for (int bulletCount = 0; bulletCount < 10; bulletCount++)
{
//draw bullet texture for every bulletsPos
spriteBatch.Draw(bullet, bulletsPos[bulletCount], Color.White);
}
spriteBatch.End();
base.Draw(gameTime);
}
最后为了让你的船移动,你应该每帧读取键盘。您只需调用一次Keyboard.GetState()。当你读它时,它返回当前按下的键,所以你需要每帧刷新它。
你应该将它添加到Update()方法的开头:
state = Keyboard.GetState();
答案 1 :(得分:0)
那是因为你在制造子弹之前试图绘制子弹。解决方案是在制作子弹之前不要绘制子弹。
有很多种方法可以做到这一点,但这是最快最肮脏的方式:
变化
for (int bulletCount = 0; bulletCount < 10; bulletCount++)
{
spriteBatch.Draw(bullets[bulletCount], bulletsPos[bulletCount], Color.White);
}
到
for (int bulletCount = 0; bulletCount < 10; bulletCount++)
{
if(bullets[bulletCount] != null)
spriteBatch.Draw(bullets[bulletCount], bulletsPos[bulletCount], Color.White);
}