所以我有一个像素精灵碰撞类,它可以部分工作,但只能在右边工作。试图向左移动导致总是发生碰撞。这是班级本身。
public Boolean collision(Texture2D first, Vector2 position1, Texture2D second, Vector2 position2)
{
//gets the bounds of the two sprites
FirstBounds = new Rectangle((int)(position1.X),
(int)(position1.Y), first.Width, first.Height);
SecondBounds = new Rectangle((int)(position2.X),
(int)(position2.Y), second.Width, second.Height);
//if they intersect.
if (FirstBounds.Intersects(SecondBounds))
{
Color[] DataA = new Color[first.Width * first.Height];
first.GetData(DataA);
Color[] DataB = new Color[second.Width * second.Height];
second.GetData(DataB);
int Top = System.Math.Max(FirstBounds.Top, SecondBounds.Top);
int Bottom = System.Math.Min(FirstBounds.Bottom, SecondBounds.Bottom);
int Left = System.Math.Max(FirstBounds.Left, SecondBounds.Left);
int Right = System.Math.Min(FirstBounds.Right, SecondBounds.Right);
for (int y = Top; y < Bottom; y++)
{
for (int x = Left; x < Right; x++)
{
Color ColorA = DataA[(x - FirstBounds.Left) + (y - FirstBounds.Top) * FirstBounds.Width];
Color ColorB = DataB[(x - SecondBounds.Left) + (y - SecondBounds.Top) * SecondBounds.Width];
if (ColorA.A > 0 && ColorB.A > 0)
{
return true;
}
}
}
return false;
}
return false;
}
这是我正在使用的整个类的代码,是的,它是主类。
/// <summary>
/// This is the main type for your game
/// </summary>
public class Game1 : Microsoft.Xna.Framework.Game
{
// all graphics classes.
GraphicsDeviceManager graphics;
SpriteBatch spriteBatch;
private AnimatedSprite animatedSprite;
private AnimatedSprite background2;
private AnimatedSprite Zero;
private KeyboardState oldState;
//starting place for Zero
Vector2 lol = new Vector2(100, 200);
Vector2 ground2 = new Vector2(0, 0);
Vector2 ground = new Vector2(0, 0);
Boolean jumping = false;
Texture2D firstback;
Texture2D texture2;
Texture2D secondback;
public Rectangle FirstBounds;
public Rectangle SecondBounds;
//Variables
int timer = 0; //checks if it should update, helps to delay the update process.
int jumptimer = 0;//uses as a timer for the amount of time you get to jump.
int jumpanimation = 0;
public Game1()
{
graphics = new GraphicsDeviceManager(this);
Content.RootDirectory = "Content";
graphics.PreferredBackBufferHeight = 900;
graphics.PreferredBackBufferWidth = 1000;
}
protected override void Initialize()
{
base.Initialize();
}
protected override void LoadContent()
{
spriteBatch = new SpriteBatch(GraphicsDevice);
firstback = Content.Load<Texture2D>("Tester");
animatedSprite = new AnimatedSprite(firstback, 1, 1);
secondback = Content.Load<Texture2D>("Tester2");
background2 = new AnimatedSprite(secondback, 1, 1);
//Creates the sprite for Zero, the main character.
texture2 = Content.Load<Texture2D>("ZeroIdle");
Zero = new AnimatedSprite(texture2, 1, 8);
ground2 = new Vector2(ground.X + firstback.Width, 0);
}
protected override void UnloadContent()
{
}
//Collision, took forever to figure out.
public Boolean collision(Texture2D first, Vector2 position1, Texture2D second, Vector2 position2)
{
//gets the bounds of the two sprites
FirstBounds = new Rectangle((int)(position1.X),
(int)(position1.Y), first.Width, first.Height);
SecondBounds = new Rectangle((int)(position2.X),
(int)(position2.Y), second.Width, second.Height);
//if they intersect.
if (FirstBounds.Intersects(SecondBounds))
{
Color[] DataA = new Color[first.Width * first.Height];
first.GetData(DataA);
Color[] DataB = new Color[second.Width * second.Height];
second.GetData(DataB);
int Top = System.Math.Max(FirstBounds.Top, SecondBounds.Top);
int Bottom = System.Math.Min(FirstBounds.Bottom, SecondBounds.Bottom);
int Left = System.Math.Max(FirstBounds.Left, SecondBounds.Left);
int Right = System.Math.Min(FirstBounds.Right, SecondBounds.Right);
for (int y = Top; y < Bottom; y++)
{
for (int x = Left; x < Right; x++)
{
Color ColorA = DataA[(x - FirstBounds.Left) + (y - FirstBounds.Top) * FirstBounds.Width];
Color ColorB = DataB[(x - SecondBounds.Left) + (y - SecondBounds.Top) * SecondBounds.Width];
if (ColorA.A > 0 && ColorB.A > 0)
{
return true;
}
}
}
return false;
}
return false;
}
protected override void Update(GameTime gameTime)
{
KeyboardState state = Keyboard.GetState();
// Allows the game to exit
if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
this.Exit();
//checks indivdual keystates, starts with if keys are down.
if (state.IsKeyDown(Keys.Right) && state.IsKeyUp(Keys.Left))
{
if (state.IsKeyDown(Keys.Up))
{
//Makes it impossible to double jump. You need to wait until you finished your jump to jump again.
if (oldState.IsKeyUp(Keys.Up) && jumping == false && (collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true))
{
texture2 = Content.Load<Texture2D>("ZeroJump");
Zero = new AnimatedSprite(texture2, 1, 14);
jumping = true;
}
}
//checks to see if you've released the right key. Makes the game update properly.
if (oldState.IsKeyUp(Keys.Right) && jumping == false && (collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true))
{
texture2 = Content.Load<Texture2D>("ZeroRunning");
Zero = new AnimatedSprite(texture2, 1, 11);
}
oldState = state;
//Causes a delay to make sure Zero updates properly and not at 60 times per second.
if (timer >=3)
{
//moves Zero.
Vector2 adding = new Vector2(5, 0);
lol = Vector2.Add(lol, adding);
Zero.Update();
timer = 0;
}
else
timer++;
Vector2 aSpeed = new Vector2(-5, 0);
ground = Vector2.Add(ground, aSpeed);
ground2 = Vector2.Add(ground2, aSpeed);
}
else if (state.IsKeyDown(Keys.Left) && state.IsKeyUp(Keys.Right))
{
if (state.IsKeyDown(Keys.Up))
{
//Makes it impossible to double jump. You need to wait until you finished your jump to jump again.
if (oldState.IsKeyUp(Keys.Up) && jumping == false && (collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true))
{
texture2 = Content.Load<Texture2D>("ZeroJump");
Zero = new AnimatedSprite(texture2, 1, 14);
jumping = true;
}
}
//checks to see if you've released the right key. Makes the game update properly.
if (oldState.IsKeyUp(Keys.Left) && jumping == false && (collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true))
{
texture2 = Content.Load<Texture2D>("ZeroRunningLeft");
Zero = new AnimatedSprite(texture2, 1, 11);
}
oldState = state;
//causes a delay in updating so Zero animates properly.
if (timer >= 3)
{
//actually moves Zero.
Vector2 adding = new Vector2(-5, 0);
lol = Vector2.Add(lol, adding);
Zero.Update();
timer = 0;
}
else
timer++;
Vector2 aSpeed = new Vector2(5, 0);
ground = Vector2.Add(ground, aSpeed);
ground2 = Vector2.Add(ground2, aSpeed);
}
//Jumping State.
if (state.IsKeyDown(Keys.Up))
{
//Makes it impossible to double jump. You need to wait until you finished your jump to jump again.
if (oldState.IsKeyUp(Keys.Up) && jumping == false && (collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true))
{
texture2 = Content.Load<Texture2D>("ZeroJump");
Zero = new AnimatedSprite(texture2, 1, 14);
jumping = true;
}
oldState = state;
}
//Section that checks if the keys are up.
if (state.IsKeyUp(Keys.Left) && state.IsKeyUp(Keys.Right) && jumping == false && (collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true))
{
texture2 = Content.Load<Texture2D>("ZeroIdle");
Zero = new AnimatedSprite(texture2, 1, 8);
timer = 0;
oldState = (new KeyboardState());
}
//Gravity effects and updates.
if (jumping == true)
{
Vector2 adding = new Vector2(0, -5);
lol = Vector2.Add(lol, adding);
//times the animation.
if (jumpanimation >= 5)
{
Zero.Update();
jumpanimation = 0;
}
else
jumpanimation++;
jumptimer++;
if (jumptimer >= 30)
{
jumping = false;
jumptimer = 0;
//whenever the timer has expired.
if (collision(firstback, ground, texture2, lol) == false)
{
texture2 = Content.Load<Texture2D>("ZeroFalling");
Zero = new AnimatedSprite(texture2, 1, 4);
}
oldState = (new KeyboardState());
}
}
else
{
if (collision(firstback, ground, texture2, lol) == false && collision(secondback, ground2, texture2, lol) == false)
{
Vector2 adding = new Vector2(0, 5);
lol = Vector2.Add(lol, adding);
}
else if ((collision(firstback, ground, texture2, lol) == true || collision(secondback, ground2, texture2, lol) == true) == true && texture2 == Content.Load<Texture2D>("ZeroFalling"))
oldState = (new KeyboardState());
}
base.Update(gameTime);
}
protected override void Draw(GameTime gameTime)
{
GraphicsDevice.Clear(Color.CornflowerBlue);
background2.Draw(spriteBatch, ground2);
Zero.Draw(spriteBatch, lol);
animatedSprite.Draw(spriteBatch, ground);
base.Draw(gameTime);
}
}
}
我不完全确定出了什么问题,感谢任何帮助。非常感谢你!
答案 0 :(得分:0)
您拥有的所有内容看起来都是正确的,因此问题可能出在其他地方,例如,位置更新太晚或太快。还有更多要发布的代码吗?
我会推荐以下教程:
http://xbox.create.msdn.com/en-US/education/tutorial/2dgame/getting_started
它将有助于正确设置动画类,因此正在使用适当的帧进行检测。