2012-03-28 4 views
1

Я просматривал другие вопросы, но просто не могу понять это. Я использую XNA в пользовательском загрузчике tilemap. Вот код. http://pastebin.com/cuatQHTbПлитка карты Обнаружение столкновений

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; 
using Microsoft.Xna.Framework.Net; 
using Microsoft.Xna.Framework.Storage; 

namespace Pressure 
{ 

    public class Game1 : Microsoft.Xna.Framework.Game 
    { 


     GraphicsDeviceManager graphics; 
     SpriteBatch spriteBatch; 
     Texture2D player; 
     Vector2 pos = Vector2.Zero; 
     Vector2 playersp = new Vector2(50.0f, 50.0f); 
     Texture2D road1; 
     Texture2D road2; 
     Texture2D brickwall; 
     Texture2D floor1; 
     Texture2D floor2; 
     Texture2D floor3; 
     Texture2D grass; 
     Texture2D sidewalk1; 
     Texture2D wood; 
     Texture2D road3; 
     private Vector2 origin; 
     KeyboardState currentState; 
     Camera camera = new Camera(); 

     Vector2 motion; 

     List<Texture2D> tiles = new List<Texture2D>(); 

     static int tileWidth = 64; 
     static int tileHeight = 64; 

     int tileMapWidth; 
     int tileMapHeight; 

     static int screenWidth; 
     static int screenHeight; 

     static int mapWidthInPixels; 
     static int mapHeightInPixels; 
     int[,] map = { 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 5, 6, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 8, 8, 8, 8, 8, 8, 8, 8, 7, 5, 6, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 8, 1, 1, 1, 2, 2, 1, 8, 7, 5, 6, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 8, 1, 1, 1, 2, 2, 1, 8, 7, 5, 5, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 8, 1, 1, 1, 1, 1, 1, 8, 7, 5, 5, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 8, 1, 3, 3, 3, 1, 1, 8, 7, 5, 6, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 8, 8, 1, 1, 8, 8, 8, 8, 7, 5, 6, 5, 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 5, 6, 5, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,}, 
       {5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,}, 
       {9, 9, 9, 5, 5, 9, 9, 9, 5, 5, 9, 9, 9, 5, 5, 5, 5, 5, 9, 9, 9, 5, 5, 9, 9, 9, 5, 5, 9,}, 
       {5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,}, 
       {7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
       {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,}, 
        }; 
     public static int ScreenWidth 
     { 
      get { return screenWidth; } 
     } 

     public static int ScreenHeight 
     { 
      get { return screenHeight; } 
     } 

     public static int MapWidthInPixels 
     { 
      get { return mapWidthInPixels; } 
     } 

     public static int MapHeightInPixels 
     { 
      get { return mapHeightInPixels; } 
     } 
     public Game1() 
     { 
      graphics = new GraphicsDeviceManager(this); 
      Content.RootDirectory = "Content"; 
     } 


     protected override void Initialize() 
     { 

      base.Initialize(); 
     } 

     protected override void LoadContent() 
     { 
      spriteBatch = new SpriteBatch(GraphicsDevice); 

      player = Content.Load<Texture2D>("haz"); 
      origin.X = player.Width /2; 
      origin.Y = player.Height /2; 
      grass = Content.Load<Texture2D>("grass"); 
      floor1 = Content.Load<Texture2D>("floor1"); 
      floor2 = Content.Load<Texture2D>("floor2"); 
      floor3 = Content.Load<Texture2D>("floor3"); 
      wood = Content.Load<Texture2D>("wood"); 
      road1 = Content.Load<Texture2D>("road1"); 
      road2 = Content.Load<Texture2D>("road2"); 
      sidewalk1 = Content.Load<Texture2D>("sidewalk1"); 
      brickwall = Content.Load<Texture2D>("brickwall"); 
      road3 = Content.Load<Texture2D>("road3"); 
      tiles.Add(grass); //0 
      tiles.Add(floor1);//1 
      tiles.Add(floor2);//2 
      tiles.Add(floor3);//3 
      tiles.Add(wood);//4 
      tiles.Add(road1);//5 
      tiles.Add(road2);//6 
      tiles.Add(sidewalk1);//7 
      tiles.Add(brickwall);//8 
      tiles.Add(road3);//9 

      tileMapWidth = map.GetLength(1); 
      tileMapHeight = map.GetLength(0); 

      mapWidthInPixels = tileMapWidth * tileWidth; 
      mapHeightInPixels = tileMapHeight * tileHeight; 

      screenWidth = GraphicsDevice.Viewport.Width; 
      screenHeight = GraphicsDevice.Viewport.Height; 
      } 


     protected override void UnloadContent() 
     { 
      } 
     private float RotationAngle; 
     private float oldx; 
     private float oldy; 

     protected override void Update(GameTime gameTime) 
     { 
      oldx = playersp.X; 
      oldy = playersp.Y; 
    currentState = Keyboard.GetState(); 
    pos = playersp; 

      if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed) 
       this.Exit(); 

      IsMouseVisible = true; 


      MouseState Mouses = Mouse.GetState(); 
      Vector2 mouseLook = new Vector2(Mouses.X, Mouses.Y); 

      motion = Vector2.Zero; 
      Vector2 direction = (playersp) - mouseLook; 
      float angle = (float)(Math.Atan2(direction.Y, direction.X)); 

      RotationAngle = angle ; 
      if (currentState.IsKeyDown(Keys.W)) 
      { 
       if (playersp.Y > screenHeight /4) 
       { 
        playersp.Y = playersp.Y - 1; 

       } 
       else 
       { 
        ScrollUp(); 

       } 
      } 
      if (currentState.IsKeyDown(Keys.A)) 
      { 
       if (playersp.X > screenWidth/4) 
       { 

         playersp.X = playersp.X - 1; 

       } 
       else 
       { 
        ScrollLeft(); 


       } 
      } 
      if (currentState.IsKeyDown(Keys.S)) 
      { 
       if (playersp.Y > screenHeight/1.5f) 
       { 
        ScrollDown(); 
       }else{ 
        playersp.Y = playersp.Y + 1; 
       } 

      } 
      if (currentState.IsKeyDown(Keys.D)) 
      { 

       if (playersp.X > screenWidth/1.5f) 
       { 

        ScrollRight(); 
       } 
       else 
       { 
        playersp.X = playersp.X + 1; 

       } 

      } 
      if (motion != Vector2.Zero) 
      { 
       motion.Normalize(); 

       camera.Position += motion * camera.Speed; 
      } 

      base.Update(gameTime); 
     } 

     private void ScrollUp() 
     { 
      motion.Y = -0.5f; 
     } 

     private void ScrollRight() 
     { 
      motion.X = 0.5f; 
     } 

     private void ScrollDown() 
     { 
      motion.Y = 0.5f; 
     } 

     private void ScrollLeft() 
     { 
      motion.X = -0.5f; 
     } 

     private Point VectorToCell(Vector2 vector) 
     { 
      return new Point(
         (int)(vector.X/tileWidth), 
         (int)(vector.Y/tileHeight)); 
     } 

     private Vector2 ViewPortVector() 
     { 
      return new Vector2(
        screenWidth + tileWidth, 
        screenHeight + tileHeight); 
     } 


     protected override void Draw(GameTime gameTime) 
     { 

      GraphicsDevice.Clear(Color.CornflowerBlue); 
      DrawMap(); 




      base.Draw(gameTime); 

     } 

     private void DrawMap() 
     { 
      Point cameraPoint = VectorToCell(camera.Position); 
      Point viewPoint = VectorToCell(camera.Position + 
           ViewPortVector()); 

      Point min = new Point(); 
      Point max = new Point(); 

      min.X = cameraPoint.X; 
      min.Y = cameraPoint.Y; 
      max.X = (int)Math.Min(viewPoint.X, map.GetLength(1)); 
      max.Y = (int)Math.Min(viewPoint.Y, map.GetLength(0)); 

      Rectangle tileRectangle = new Rectangle(
        0, 
        0, 
        tileWidth, 
        tileHeight); 

      spriteBatch.Begin(); 

      for (int y = min.Y; y < max.Y; y++) 
      { 
       for (int x = min.X; x < max.X; x++) 
       { 
        tileRectangle.X = x * tileWidth - (int)camera.Position.X; 
        tileRectangle.Y = y * tileHeight - (int)camera.Position.Y; 

        spriteBatch.Draw(tiles[map[y, x]], 
         tileRectangle, 
         Color.White); 
        spriteBatch.Draw(player, pos, null, Color.White, RotationAngle, 
     origin, 1.0f, SpriteEffects.None, 0f); 
       } 
      } 

      spriteBatch.End(); 
     } 

    } 
} 

Как бы определить положение плитки и убедиться, что игрок не входит в эту плитку? благодаря!

+0

Не уверен, что я понимаю ваш вопрос: у вас есть карта 0-9; плитки, связанные с каждым значением; Предполагаю, что вы знаете позицию игрока на карте; вы можете проверить, где они хотят двигаться, это тип плитки, который они не должны. В этом случае не меняйте положение игрока - я что-то не понял? Или это решение, о котором вы спрашивали? – Attila

+0

@ user1042757, вставьте код, который вам нужен, чтобы задать вопрос, а не ссылку. Если код длиннее 10 строк, скорее всего, ваш вопрос будет о чем-то другом ... поэтому просмотрите свой код и задайте вопрос вместе, чтобы убедиться, что оба имеют смысл вместе. –

+0

@Attila Я хочу найти, если игрок собирается переместиться в неправильную плитку, а затем убедитесь, что он не может двигаться. Давайте скажем, как в движении , когда игрок нажимает кнопку, чтобы переместить спрайт, который я хочу проверить, и посмотреть, какая плитка движется, и если он движется в «стенную» плитку, я хочу убедиться, что она не может. – user1042757

ответ

1

Вы могли бы сделать что-то вроде этого:

private static float scalingFactor = 10; 
private static float mapSizeX = 19; 
private static float mapSizeY = 29; 

в Update:

if (playersp.Y > screenHeight /4) { 
    int mapX = (int) (playersp.X/scalingFactor); 
    int mapY = (int) (playersp.Y/scalingFactor) - 1; 
    if (isMovable(mapX, mapY)) { 
    playersp.Y = playersp.Y - scalingFactor; 
    } 
} else { 
    ScrollUp(); 
} 

и новый метод:

public bool isMovable(int mapX, int mapY) 
{ 
    if (mapX < 0 || mapX > 19 || mapY < 0 || mapY > 29) { 
    return false; 
    } 

    int tile = map[mapX, mapY]; 
    if (tile == 4 || tile == 8) { 
    return false; 
    } 

    return true; 
} 

Аналогично для других направлений.

Вышеупомянутый код вызывает функцию isMovable, чтобы решить, может ли игрок перемещаться в новое место в зависимости от типа плитки, хранящейся на карте в этой позиции. Решение ложно (игрок не может двигаться туда), если это деревянная или кирпичная стена, иначе это правда.

Коэффициент масштабирования - это отображение между положением экрана (зафиксировано в playersp) и картой плитки. В этом случае каждая плитка эквивалентна 10 экранным «пикселям» (вы можете разбить ее на две отдельные шкалы, если хотите: один для X-размера, другой для Y).

Примечание. Вам необходимо убедиться в правильности значений mapSizeX и mapSizeY.

Было бы лучше, если бы вы вводили именованные константы для типа плитки вместо использования чисел - это сделает ваш код более читаемым (для вас в будущем и для других, читающих его).

EDIT: обновленный код & объяснения

+0

Большое вам спасибо! Это все для меня! Я обязательно попробую, и я отчитаюсь в течение часа. – user1042757

+0

«Индекс находился за пределами массива». Это дает мне это прямо здесь: if (isMovable (карта [новыйX, новыйY])) – user1042757

+0

Что такое значение newX и newY? Карта 19 * 29 (если я правильно подсчитал), поэтому индексы не должны быть больше. Я считаю, что вы инициализируете позицию игрока до 50, 50, которая находится за пределами границ (даже если они перемещаются один раз).Если значение 50,50 правильное, вам нужно уменьшить его для индексов карты, иначе выбрать допустимую начальную координату. В любом случае вам необходимо убедиться, что пользователь не покидает карту, или вы получите ту же ошибку. – Attila

Смежные вопросы