Fixed the discrepancy between the screen coords and the game coords and also fixed mouse problem when zoomed out too far.
This commit is contained in:
@@ -1,7 +1,4 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Collector;
|
||||
using Collector.Character;
|
||||
using Collector.Dimension;
|
||||
using Microsoft.Xna.Framework;
|
||||
using Microsoft.Xna.Framework.Content;
|
||||
@@ -9,201 +6,198 @@ using Microsoft.Xna.Framework.Graphics;
|
||||
using Microsoft.Xna.Framework.Input;
|
||||
using MonoGame.Extended;
|
||||
|
||||
public class InputController : IRestrictions
|
||||
namespace Collector.Character
|
||||
{
|
||||
private readonly PlayerMouse _playerMouse;
|
||||
private readonly OrthographicCamera _cam;
|
||||
private readonly Dictionary<string, Rectangle[]> _animations;
|
||||
private readonly Texture2D _texture;
|
||||
private readonly SpriteBatch _spriteBatch;
|
||||
private string Input { get; set; }
|
||||
private int _frameNumber;
|
||||
private int _timeSinceLastFrame;
|
||||
|
||||
|
||||
public InputController(PlayerMouse playerMouse, OrthographicCamera cam, SpriteBatch spriteBatch, ContentManager contentManager)
|
||||
public class InputController : IRestrictions
|
||||
{
|
||||
Input = "Down";
|
||||
_playerMouse = playerMouse;
|
||||
_cam = cam;
|
||||
_spriteBatch = spriteBatch;
|
||||
_frameNumber = 0;
|
||||
_texture = contentManager.Load<Texture2D>("man");
|
||||
_animations = new Dictionary<string, Rectangle[]>
|
||||
{
|
||||
["Up"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0, 0, 32, 32),
|
||||
new Rectangle(32 * 1, 0, 32, 32),
|
||||
new Rectangle(32 * 2, 0, 32, 32),
|
||||
new Rectangle(32 * 3, 0, 32, 32)
|
||||
},
|
||||
["Right"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0 + 32 * 4, 32, 32, 32),
|
||||
new Rectangle(32 * 1 + 32 * 4, 32, 32, 32),
|
||||
new Rectangle(32 * 2 + 32 * 4, 32, 32, 32),
|
||||
new Rectangle(32 * 3 + 32 * 4, 32, 32, 32)
|
||||
},
|
||||
["UpRight"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0 + 32 * 4, 32 * 2, 32, 32),
|
||||
new Rectangle(32 * 1 + 32 * 4, 32 * 2, 32, 32),
|
||||
new Rectangle(32 * 2 + 32 * 4, 32 * 2, 32, 32),
|
||||
new Rectangle(32 * 3 + 32 * 4, 32 * 2, 32, 32)
|
||||
},
|
||||
["DownRight"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0 + 32 * 4, 32 * 3, 32, 32),
|
||||
new Rectangle(32 * 1 + 32 * 4, 32 * 3, 32, 32),
|
||||
new Rectangle(32 * 2 + 32 * 4, 32 * 3, 32, 32),
|
||||
new Rectangle(32 * 3 + 32 * 4, 32 * 3, 32, 32)
|
||||
},
|
||||
["Left"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0, 32, 32, 32),
|
||||
new Rectangle(32 * 1, 32, 32, 32),
|
||||
new Rectangle(32 * 2, 32, 32, 32),
|
||||
new Rectangle(32 * 3, 32, 32, 32)
|
||||
},
|
||||
["UpLeft"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0, 32 * 2, 32, 32),
|
||||
new Rectangle(32 * 1, 32 * 2, 32, 32),
|
||||
new Rectangle(32 * 2, 32 * 2, 32, 32),
|
||||
new Rectangle(32 * 3, 32 * 2, 32, 32)
|
||||
},
|
||||
["DownLeft"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0, 32, 32, 32),
|
||||
new Rectangle(32 * 1, 32, 32, 32),
|
||||
new Rectangle(32 * 2, 32, 32, 32),
|
||||
new Rectangle(32 * 3, 32, 32, 32)
|
||||
},
|
||||
["Down"] = new[]
|
||||
{
|
||||
new Rectangle(32 * 0 + 32 * 4, 0, 32, 32),
|
||||
new Rectangle(32 * 1 + 32 * 4, 0, 32, 32),
|
||||
new Rectangle(32 * 2 + 32 * 4, 0, 32, 32),
|
||||
new Rectangle(32 * 3 + 32 * 4, 0, 32, 32)
|
||||
},
|
||||
};
|
||||
}
|
||||
private readonly PlayerMouse _playerMouse;
|
||||
private readonly OrthographicCamera _cam;
|
||||
private readonly Dictionary<string, Rectangle[]> _animations;
|
||||
private readonly Texture2D _texture;
|
||||
private readonly SpriteBatch _spriteBatch;
|
||||
private string Input { get; set; }
|
||||
private int _frameNumber;
|
||||
private int _timeSinceLastFrame;
|
||||
|
||||
public void PlayerInput(Main main, PlayerMouse playerMouse, GameTime gameTime)
|
||||
{
|
||||
var keyboardState = Keyboard.GetState();
|
||||
var mouseState = Mouse.GetState();
|
||||
const int movementSpeed = IRestrictions.MovementSpeed;
|
||||
if (keyboardState.IsKeyDown(Keys.Escape))
|
||||
{
|
||||
Quit(main);
|
||||
}
|
||||
if (keyboardState.IsKeyUp(Keys.W) && keyboardState.IsKeyUp(Keys.A) && keyboardState.IsKeyUp(Keys.S) && keyboardState.IsKeyUp(Keys.D))
|
||||
{
|
||||
Input = Input.Contains("Right") ? "DownRight" : "DownLeft";
|
||||
|
||||
_frameNumber = 0;
|
||||
_playerMouse.Draw();
|
||||
}
|
||||
if (keyboardState.IsKeyDown(Keys.W) && keyboardState.IsKeyDown(Keys.D))
|
||||
public InputController(PlayerMouse playerMouse, OrthographicCamera cam, SpriteBatch spriteBatch, ContentManager contentManager)
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "UpRight";
|
||||
Player.Y += -movementSpeed;
|
||||
Player.X += movementSpeed;
|
||||
_cam.Move(new Vector2(movementSpeed, -movementSpeed));
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.W) && keyboardState.IsKeyDown(Keys.A))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "UpLeft";
|
||||
Player.Y += -movementSpeed;
|
||||
Player.X += -movementSpeed;
|
||||
_cam.Move(new Vector2(-movementSpeed, -movementSpeed));
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.S) && keyboardState.IsKeyDown(Keys.D))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "DownRight";
|
||||
Player.Y += movementSpeed;
|
||||
Player.X += movementSpeed;
|
||||
_cam.Move(new Vector2(movementSpeed, movementSpeed));
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.S) && keyboardState.IsKeyDown(Keys.A))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "DownLeft";
|
||||
Player.Y += movementSpeed;
|
||||
Player.X += -movementSpeed;
|
||||
_cam.Move(new Vector2(-movementSpeed, movementSpeed));
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.W))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "Up";
|
||||
Player.Y += -movementSpeed;
|
||||
_cam.Move(new Vector2(0, -movementSpeed));
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.A))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Player.X += -movementSpeed;
|
||||
_cam.Move(new Vector2(-movementSpeed, 0));
|
||||
Input = "Left";
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.S))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Player.Y += movementSpeed;
|
||||
_cam.Move(new Vector2(0, movementSpeed));
|
||||
Input = "Down";
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.D))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Player.X += movementSpeed;
|
||||
_cam.Move(new Vector2(movementSpeed, 0));
|
||||
Input = "Right";
|
||||
}
|
||||
if (keyboardState.IsKeyDown(Keys.Q))
|
||||
{
|
||||
_cam.ZoomIn(0.01f);
|
||||
}
|
||||
if (keyboardState.IsKeyDown(Keys.E))
|
||||
{
|
||||
_cam.ZoomOut(0.01f);
|
||||
}
|
||||
|
||||
if (mouseState.LeftButton == ButtonState.Pressed)
|
||||
{
|
||||
Chunks.RemoveBlock(playerMouse.GetSelectedXTile(),playerMouse.GetSelectedYTile());
|
||||
}
|
||||
if (mouseState.RightButton == ButtonState.Pressed)
|
||||
{
|
||||
Chunks.PlaceBlock(playerMouse.GetSelectedXTile(),playerMouse.GetSelectedYTile(),Blocks.BlockWood);
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateAnimationFrame(GameTime gameTime)
|
||||
{
|
||||
_timeSinceLastFrame += gameTime.ElapsedGameTime.Milliseconds;
|
||||
if (_timeSinceLastFrame <= 99) return;
|
||||
_frameNumber++;
|
||||
_timeSinceLastFrame = 0;
|
||||
if (_frameNumber > 3)
|
||||
{
|
||||
_playerMouse = playerMouse;
|
||||
_cam = cam;
|
||||
_spriteBatch = spriteBatch;
|
||||
_frameNumber = 0;
|
||||
_texture = contentManager.Load<Texture2D>("man");
|
||||
const int tileSize = 32;
|
||||
_animations = new Dictionary<string, Rectangle[]>
|
||||
{
|
||||
["Up"] = new[]
|
||||
{
|
||||
new Rectangle(0, 0, tileSize, tileSize),
|
||||
new Rectangle(1, 0, tileSize, tileSize),
|
||||
new Rectangle(2, 0, tileSize, tileSize),
|
||||
new Rectangle(3, 0, tileSize, tileSize)
|
||||
},
|
||||
["Right"] = new[]
|
||||
{
|
||||
new Rectangle(0 + 4, 1, tileSize, tileSize),
|
||||
new Rectangle(1 + 4, 1, tileSize, tileSize),
|
||||
new Rectangle(2 + 4, 1, tileSize, tileSize),
|
||||
new Rectangle(3 + 4, 1, tileSize, tileSize)
|
||||
},
|
||||
["UpRight"] = new[]
|
||||
{
|
||||
new Rectangle(0 + 4, 2, tileSize, tileSize),
|
||||
new Rectangle(1 + 4, 2, tileSize, tileSize),
|
||||
new Rectangle(2 + 4, 2, tileSize, tileSize),
|
||||
new Rectangle(3 + 4, 2, tileSize, tileSize)
|
||||
},
|
||||
["DownRight"] = new[]
|
||||
{
|
||||
new Rectangle(0 + 4, 3, tileSize, tileSize),
|
||||
new Rectangle(1 + 4, 3, tileSize, tileSize),
|
||||
new Rectangle(2 + 4, 3, tileSize, tileSize),
|
||||
new Rectangle(3 + 4, 3, tileSize, tileSize)
|
||||
},
|
||||
["Left"] = new[]
|
||||
{
|
||||
new Rectangle(0, 1, tileSize, tileSize),
|
||||
new Rectangle(1, 1, tileSize, tileSize),
|
||||
new Rectangle(2, 1, tileSize, tileSize),
|
||||
new Rectangle(3, 1, tileSize, tileSize)
|
||||
},
|
||||
["UpLeft"] = new[]
|
||||
{
|
||||
new Rectangle(0, 2, tileSize, tileSize),
|
||||
new Rectangle(1, 2, tileSize, tileSize),
|
||||
new Rectangle(2, 2, tileSize, tileSize),
|
||||
new Rectangle(3, 2, tileSize, tileSize)
|
||||
},
|
||||
["DownLeft"] = new[]
|
||||
{
|
||||
new Rectangle(0, 1, tileSize, tileSize),
|
||||
new Rectangle(1, 1, tileSize, tileSize),
|
||||
new Rectangle(2, 1, tileSize, tileSize),
|
||||
new Rectangle(3, 1, tileSize, tileSize)
|
||||
},
|
||||
["Down"] = new[]
|
||||
{
|
||||
new Rectangle(0 + 4, 0, tileSize, tileSize),
|
||||
new Rectangle(1 + 4, 0, tileSize, tileSize),
|
||||
new Rectangle(2 + 4, 0, tileSize, tileSize),
|
||||
new Rectangle(3 + 4, 0, tileSize, tileSize)
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
private static void Quit(Game main)
|
||||
{
|
||||
main.Exit();
|
||||
}
|
||||
public void PlayerInput(Main main, PlayerMouse playerMouse, GameTime gameTime)
|
||||
{
|
||||
const int movementSpeed = IRestrictions.MovementSpeed;
|
||||
var keyboardState = Keyboard.GetState();
|
||||
var mouseState = Mouse.GetState();
|
||||
if (keyboardState.IsKeyDown(Keys.Escape))
|
||||
{
|
||||
Quit(main);
|
||||
}
|
||||
if (keyboardState.IsKeyUp(Keys.W) && keyboardState.IsKeyUp(Keys.A) && keyboardState.IsKeyUp(Keys.S) && keyboardState.IsKeyUp(Keys.D))
|
||||
{
|
||||
Input = Input.Contains("Right") ? "DownRight" : "DownLeft";
|
||||
|
||||
public void Draw()
|
||||
{
|
||||
_spriteBatch.Draw(_texture, new Vector2(Player.X, Player.Y), _animations[Input][_frameNumber], Color.White);
|
||||
_frameNumber = 0;
|
||||
_playerMouse.Draw();
|
||||
}
|
||||
if (keyboardState.IsKeyDown(Keys.W) && keyboardState.IsKeyDown(Keys.D))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "UpRight";
|
||||
Player.Move(_cam,movementSpeed,-movementSpeed);
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.W) && keyboardState.IsKeyDown(Keys.A))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "UpLeft";
|
||||
Player.Move(_cam,-movementSpeed,-movementSpeed);
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.S) && keyboardState.IsKeyDown(Keys.D))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "DownRight";
|
||||
Player.Move(_cam,movementSpeed,movementSpeed);
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.S) && keyboardState.IsKeyDown(Keys.A))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "DownLeft";
|
||||
Player.Move(_cam,-movementSpeed,movementSpeed);
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.W))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Input = "Up";
|
||||
Player.Move(_cam,0,-movementSpeed);
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.A))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Player.Move(_cam,-movementSpeed,0);
|
||||
Input = "Left";
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.S))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Player.Move(_cam,0,movementSpeed);
|
||||
Input = "Down";
|
||||
}
|
||||
else if (keyboardState.IsKeyDown(Keys.D))
|
||||
{
|
||||
UpdateAnimationFrame(gameTime);
|
||||
Player.Move(_cam,movementSpeed,0);
|
||||
Input = "Right";
|
||||
}
|
||||
if (keyboardState.IsKeyDown(Keys.Q))
|
||||
{
|
||||
_cam.ZoomIn(1f);
|
||||
}
|
||||
if (keyboardState.IsKeyDown(Keys.E))
|
||||
{
|
||||
_cam.ZoomOut(1f);
|
||||
}
|
||||
|
||||
if (mouseState.LeftButton == ButtonState.Pressed)
|
||||
{
|
||||
Chunks.RemoveBlock(PlayerMouse.GetSelectedX(),PlayerMouse.GetSelectedY());
|
||||
}
|
||||
if (mouseState.RightButton == ButtonState.Pressed)
|
||||
{
|
||||
Chunks.PlaceBlock(PlayerMouse.GetSelectedX(),PlayerMouse.GetSelectedY(),Blocks.BlockWood);
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateAnimationFrame(GameTime gameTime)
|
||||
{
|
||||
_timeSinceLastFrame += gameTime.ElapsedGameTime.Milliseconds;
|
||||
if (_timeSinceLastFrame <= 99) return;
|
||||
_frameNumber++;
|
||||
_timeSinceLastFrame = 0;
|
||||
if (_frameNumber > 3)
|
||||
{
|
||||
_frameNumber = 0;
|
||||
}
|
||||
}
|
||||
|
||||
private static void Quit(Game main)
|
||||
{
|
||||
main.Exit();
|
||||
}
|
||||
|
||||
public void Draw()
|
||||
{
|
||||
_spriteBatch.Draw(
|
||||
_texture
|
||||
,Player.PlayerBounds
|
||||
,_animations[Input][_frameNumber]
|
||||
,Color.White
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,19 +1,35 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Collector.Dimension;
|
||||
using Humper;
|
||||
using Microsoft.Xna.Framework;
|
||||
using Microsoft.Xna.Framework.Media;
|
||||
using MonoGame.Extended;
|
||||
using MonoGame.Extended.Collections;
|
||||
using Collision = Collector.Dimension.Collision;
|
||||
|
||||
namespace Collector.Character
|
||||
{
|
||||
public class Player : IRestrictions
|
||||
{
|
||||
public static int X { get; set; }
|
||||
public static int Y { get; set; }
|
||||
public Dictionary<string,Rectangle> Animation { get; set; }
|
||||
//private Inventory PlayerInventory { get; }
|
||||
public static int X { get; private set; }
|
||||
public static int Y { get; private set; }
|
||||
private static Dictionary<string, Rectangle> Animation { get; set; }
|
||||
public static Rectangle PlayerBounds;
|
||||
|
||||
public Player(int x, int y) {
|
||||
X = x<<IRestrictions.TileShift;
|
||||
Y = y<<IRestrictions.TileShift;
|
||||
//PlayerInventory = new Inventory();
|
||||
public Player(int x, int y)
|
||||
{
|
||||
PlayerBounds = new Rectangle(X,Y,IRestrictions.TileSize,IRestrictions.TileSize);
|
||||
X = x;
|
||||
Y = y;
|
||||
}
|
||||
|
||||
public static void Move(OrthographicCamera cam, int x, int y)
|
||||
{
|
||||
X += x;
|
||||
Y += y;
|
||||
cam.Move(new Vector2(x+IRestrictions.TileSize/2, y+IRestrictions.TileSize/2));
|
||||
PlayerBounds.Location = new Point(X,Y);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,3 +1,4 @@
|
||||
using System;
|
||||
using Microsoft.Xna.Framework;
|
||||
using Microsoft.Xna.Framework.Content;
|
||||
using Microsoft.Xna.Framework.Graphics;
|
||||
@@ -9,7 +10,7 @@ namespace Collector.Character
|
||||
public class PlayerMouse : IRestrictions
|
||||
{
|
||||
private readonly SpriteBatch _spriteBatch;
|
||||
private readonly OrthographicCamera _cam;
|
||||
private static OrthographicCamera _cam;
|
||||
private Texture2D Crosshair { get; set; }
|
||||
|
||||
public PlayerMouse(ContentManager contentManager, SpriteBatch spriteBatch, OrthographicCamera cam)
|
||||
@@ -18,30 +19,24 @@ namespace Collector.Character
|
||||
_cam = cam;
|
||||
Crosshair = contentManager.Load<Texture2D>("crosshair");
|
||||
}
|
||||
|
||||
public void Draw()
|
||||
{
|
||||
_spriteBatch.Draw(Crosshair,new Vector2(GetSelectedX(),GetSelectedY()), Color.White);
|
||||
}
|
||||
|
||||
public int GetSelectedX()
|
||||
{
|
||||
return ((int) (Mouse.GetState().X + _cam.Position.X) >> 5) << 5;
|
||||
_spriteBatch.Draw(
|
||||
Crosshair,
|
||||
new Rectangle(GetSelectedX(),GetSelectedY(),1,1),
|
||||
new Rectangle(0,0,32,32),
|
||||
Color.White
|
||||
);
|
||||
}
|
||||
|
||||
public int GetSelectedY()
|
||||
public static int GetSelectedX()
|
||||
{
|
||||
return ((int) (Mouse.GetState().Y + _cam.Position.Y) >> 5) << 5;
|
||||
}
|
||||
|
||||
public int GetSelectedXTile()
|
||||
{
|
||||
return (int) (Mouse.GetState().X + _cam.Position.X) >> 5;
|
||||
return (int) Math.Floor(_cam.ScreenToWorld(Mouse.GetState().X,Mouse.GetState().Y).X);
|
||||
}
|
||||
|
||||
public int GetSelectedYTile()
|
||||
public static int GetSelectedY()
|
||||
{
|
||||
return (int) (Mouse.GetState().Y + _cam.Position.Y) >> 5;
|
||||
return (int) Math.Floor(_cam.ScreenToWorld(Mouse.GetState().X,Mouse.GetState().Y).Y);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -3,7 +3,8 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Collector.ThirdPartyCode;
|
||||
using Microsoft.Xna.Framework.Graphics;
|
||||
using Humper;
|
||||
using Microsoft.Xna.Framework;
|
||||
|
||||
namespace Collector.Dimension
|
||||
{
|
||||
@@ -11,7 +12,10 @@ namespace Collector.Dimension
|
||||
{
|
||||
public static Dictionary<Tuple<int, int, int>, Blocks> LoadedChunks { get; } = new Dictionary<Tuple<int, int, int>, Blocks>();
|
||||
private static readonly Dictionary<Tuple<int, int, int>, Blocks> SavedChunks = new Dictionary<Tuple<int, int, int>, Blocks>();
|
||||
|
||||
private static readonly Dictionary<Tuple<int, int>, Collision> savedCollisions = new Dictionary<Tuple<int, int>, Collision>();
|
||||
public static readonly Dictionary<Tuple<int,int>, Collision> loadedCollisions = new Dictionary<Tuple<int, int>, Collision>();
|
||||
|
||||
|
||||
private static readonly OpenSimplexNoise Gen1 = new OpenSimplexNoise(IRestrictions.Seed+ 1);
|
||||
private static readonly OpenSimplexNoise Gen2 = new OpenSimplexNoise(IRestrictions.Seed);
|
||||
|
||||
@@ -25,28 +29,37 @@ namespace Collector.Dimension
|
||||
|
||||
private static void SetBlock(int x, int y, int z, Blocks name)
|
||||
{
|
||||
LoadedChunks[new Tuple<int, int, int>(x, y, z)] = name;
|
||||
SavedChunks[new Tuple<int,int,int>(x, y, z)] = name;
|
||||
var tuple = new Tuple<int, int, int>(x, y, z);
|
||||
var pair = new Tuple<int, int>(x, y);
|
||||
|
||||
loadedCollisions[pair] = new Collision(x,y,IRestrictions.TileSize,false);
|
||||
savedCollisions[pair] = new Collision(x,y,IRestrictions.TileSize,false);
|
||||
LoadedChunks[tuple] = name;
|
||||
SavedChunks[tuple] = name;
|
||||
}
|
||||
|
||||
public static void PlaceBlock(int x, int y, Blocks name)
|
||||
{
|
||||
var triple = new Tuple<int, int, int>(x, y, 1);
|
||||
if (!LoadedChunks.ContainsKey(triple)) return;
|
||||
if (LoadedChunks[triple].Equals(Blocks.BlockAir))
|
||||
var tuple = new Tuple<int, int, int>(x, y, 1);
|
||||
if (!LoadedChunks.ContainsKey(tuple)) return;
|
||||
if (LoadedChunks[tuple].Equals(Blocks.BlockAir))
|
||||
{
|
||||
SetBlock(x, y, 1, name);
|
||||
}
|
||||
}
|
||||
|
||||
public static void RemoveBlock(int x, int y){
|
||||
var triple = new Tuple<int, int, int>(x, y, 1);
|
||||
var tuple = new Tuple<int, int, int>(x, y, 1);
|
||||
var pair = new Tuple<int,int>(x,y);
|
||||
|
||||
if (!LoadedChunks.ContainsKey(triple)) return;
|
||||
if (LoadedChunks[triple].Equals(Blocks.BlockAir)) return;
|
||||
if (!LoadedChunks.ContainsKey(tuple)) return;
|
||||
if (LoadedChunks[tuple].Equals(Blocks.BlockAir)) return;
|
||||
|
||||
LoadedChunks[triple] = Blocks.BlockAir;
|
||||
SavedChunks[triple] = Blocks.BlockAir;
|
||||
loadedCollisions[pair] = null;
|
||||
savedCollisions[pair] = null;
|
||||
|
||||
LoadedChunks[tuple] = Blocks.BlockAir;
|
||||
SavedChunks[tuple] = Blocks.BlockAir;
|
||||
}
|
||||
|
||||
public static void UngenerateChunk(int x, int y) {
|
||||
|
||||
18
Collector/src/Dimension/Collision.cs
Normal file
18
Collector/src/Dimension/Collision.cs
Normal file
@@ -0,0 +1,18 @@
|
||||
using Microsoft.Xna.Framework;
|
||||
|
||||
namespace Collector.Dimension
|
||||
{
|
||||
public class Collision
|
||||
{
|
||||
private readonly int _tileWidth;
|
||||
private bool _entity;
|
||||
public Rectangle Rectangle { get; private set; }
|
||||
|
||||
public Collision(int x, int y,int tileWidth, bool entity)
|
||||
{
|
||||
_entity = entity;
|
||||
_tileWidth = tileWidth;
|
||||
Rectangle = new Rectangle(x,y,tileWidth,tileWidth);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -4,7 +4,8 @@ using Collector.Character;
|
||||
namespace Collector.Dimension
|
||||
{
|
||||
public static class World {
|
||||
private static void GenerateWorld(int x, int y) {
|
||||
private static void GenerateWorld(int x, int y)
|
||||
{
|
||||
if (Chunks.IsEmpty(x, y)) {
|
||||
Chunks.GenerateChunk(x, y);
|
||||
}
|
||||
@@ -21,8 +22,8 @@ namespace Collector.Dimension
|
||||
for (var i = -(IRestrictions.RenderDistance); i < IRestrictions.RenderDistance; i++) {
|
||||
for (var j = -(IRestrictions.RenderDistance); j < IRestrictions.RenderDistance; j++) {
|
||||
GenerateWorld(
|
||||
i + Player.X / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize),
|
||||
j + Player.Y / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)
|
||||
i + Player.X / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize),
|
||||
j + Player.Y / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -32,23 +33,23 @@ namespace Collector.Dimension
|
||||
for (var i = -IRestrictions.RenderDistance; i < IRestrictions.RenderDistance+1; i++) {
|
||||
//Down
|
||||
UngenerateWorld(
|
||||
Player.X / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)+i,
|
||||
(Player.Y / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))+3
|
||||
Player.X / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)+i,
|
||||
(Player.Y / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))+IRestrictions.RenderDistance
|
||||
);
|
||||
//Up
|
||||
UngenerateWorld(
|
||||
Player.X / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)+i-1,
|
||||
(Player.Y / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))-4
|
||||
Player.X / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)+i,
|
||||
(Player.Y / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))-IRestrictions.RenderDistance
|
||||
);
|
||||
//Right
|
||||
UngenerateWorld(
|
||||
Player.X / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)-4,
|
||||
(Player.Y / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))+i
|
||||
Player.X / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)-IRestrictions.RenderDistance,
|
||||
(Player.Y / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))+i
|
||||
);
|
||||
//Left
|
||||
UngenerateWorld(
|
||||
Player.X / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)+3,
|
||||
(Player.Y / (IRestrictions.TileSize * IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))+i
|
||||
Player.X / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize)+IRestrictions.RenderDistance,
|
||||
(Player.Y / (IRestrictions.SuperChunkSize * IRestrictions.ChunkSize))+i
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -27,8 +27,8 @@ namespace Collector.Dimension
|
||||
batch.Draw(
|
||||
Main.Materials[Chunks.LoadedChunks[chunkpair]],
|
||||
new Rectangle(
|
||||
chunkpair.Item1 << IRestrictions.TileShift,
|
||||
chunkpair.Item2 << IRestrictions.TileShift,
|
||||
chunkpair.Item1,
|
||||
chunkpair.Item2,
|
||||
IRestrictions.TileSize, IRestrictions.TileSize
|
||||
),
|
||||
Color.White
|
||||
|
||||
@@ -1,320 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
//Quadtree code
|
||||
//https://github.com/futurechris/QuadTree
|
||||
|
||||
namespace QuadTree
|
||||
{
|
||||
|
||||
public class QuadTree<T>
|
||||
{
|
||||
private static Stack<Branch> _branchPool = new Stack<Branch>();
|
||||
private static Stack<Leaf> _leafPool = new Stack<Leaf>();
|
||||
|
||||
private readonly Branch _root;
|
||||
private readonly int _splitCount;
|
||||
private readonly int _depthLimit;
|
||||
private readonly Dictionary<T, Leaf> _leafLookup = new Dictionary<T, Leaf>();
|
||||
|
||||
|
||||
public QuadTree(int splitCount, int depthLimit, ref Quad region)
|
||||
{
|
||||
_splitCount = splitCount;
|
||||
_depthLimit = depthLimit;
|
||||
_root = CreateBranch(this, null, 0, ref region);
|
||||
}
|
||||
|
||||
public QuadTree(int splitCount, int depthLimit, Quad region)
|
||||
: this(splitCount, depthLimit, ref region)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public QuadTree(int splitCount, int depthLimit, float x, float y, float width, float height)
|
||||
: this(splitCount, depthLimit, new Quad(x, y, x + width, y + height))
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
_root.Clear();
|
||||
_root.Tree = this;
|
||||
_leafLookup.Clear();
|
||||
}
|
||||
|
||||
|
||||
public static void ClearPools()
|
||||
{
|
||||
_branchPool = new Stack<Branch>();
|
||||
_leafPool = new Stack<Leaf>();
|
||||
}
|
||||
|
||||
|
||||
private void Insert(T value, ref Quad quad)
|
||||
{
|
||||
if (!_leafLookup.TryGetValue(value, out var leaf))
|
||||
{
|
||||
leaf = CreateLeaf(value, ref quad);
|
||||
_leafLookup.Add(value, leaf);
|
||||
}
|
||||
_root.Insert(leaf);
|
||||
}
|
||||
|
||||
public void Insert(T value, Quad quad)
|
||||
{
|
||||
Insert(value, ref quad);
|
||||
}
|
||||
|
||||
public void Insert(T value, float x, float y, float width, float height)
|
||||
{
|
||||
var quad = new Quad(x, y, x + width, y + height);
|
||||
Insert(value, ref quad);
|
||||
}
|
||||
|
||||
private bool SearchArea(ref Quad quad, ref List<T> values)
|
||||
{
|
||||
if (values != null)
|
||||
values.Clear();
|
||||
else
|
||||
values = new List<T>();
|
||||
_root.SearchQuad(ref quad, values);
|
||||
return values.Count > 0;
|
||||
}
|
||||
|
||||
public bool SearchArea(Quad quad, ref List<T> values)
|
||||
{
|
||||
return SearchArea(ref quad, ref values);
|
||||
}
|
||||
|
||||
public bool SearchArea(float x, float y, float width, float height, ref List<T> values)
|
||||
{
|
||||
var quad = new Quad(x, y, x + width, y + height);
|
||||
return SearchArea(ref quad, ref values);
|
||||
}
|
||||
|
||||
public bool SearchPoint(float x, float y, ref List<T> values)
|
||||
{
|
||||
if (values != null)
|
||||
values.Clear();
|
||||
else
|
||||
values = new List<T>();
|
||||
_root.SearchPoint(x, y, values);
|
||||
return values.Count > 0;
|
||||
}
|
||||
|
||||
public bool FindCollisions(T value, ref List<T> values)
|
||||
{
|
||||
if (values != null)
|
||||
values.Clear();
|
||||
else
|
||||
values = new List<T>(_leafLookup.Count);
|
||||
|
||||
if (!_leafLookup.TryGetValue(value, out var leaf)) return false;
|
||||
var branch = leaf.Branch;
|
||||
|
||||
//Add the leaf's siblings (prevent it from colliding with itself)
|
||||
if (branch.Leaves.Count > 0)
|
||||
foreach (var t in branch.Leaves)
|
||||
if (leaf != t && leaf.Quad.Intersects(ref t.Quad))
|
||||
values.Add(t.Value);
|
||||
|
||||
//Add the branch's children
|
||||
if (branch.Split)
|
||||
for (var i = 0; i < 4; ++i)
|
||||
if (branch.Branches[i] != null)
|
||||
branch.Branches[i].SearchQuad(ref leaf.Quad, values);
|
||||
|
||||
//Add all leaves back to the root
|
||||
branch = branch.Parent;
|
||||
while (branch != null)
|
||||
{
|
||||
if (branch.Leaves.Count > 0)
|
||||
foreach (var t in branch.Leaves)
|
||||
if (leaf.Quad.Intersects(ref t.Quad))
|
||||
values.Add(t.Value);
|
||||
|
||||
branch = branch.Parent;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public int CountBranches()
|
||||
{
|
||||
var count = 0;
|
||||
CountBranches(_root, ref count);
|
||||
return count;
|
||||
}
|
||||
|
||||
private static void CountBranches(Branch branch, ref int count)
|
||||
{
|
||||
++count;
|
||||
if (!branch.Split) return;
|
||||
for (var i = 0; i < 4; ++i)
|
||||
if (branch.Branches[i] != null)
|
||||
CountBranches(branch.Branches[i], ref count);
|
||||
}
|
||||
|
||||
private static Branch CreateBranch(QuadTree<T> tree, Branch parent, int branchDepth, ref Quad quad)
|
||||
{
|
||||
var branch = _branchPool.Count > 0 ? _branchPool.Pop() : new Branch();
|
||||
branch.Tree = tree;
|
||||
branch.Parent = parent;
|
||||
branch.Split = false;
|
||||
branch.Depth = branchDepth;
|
||||
var midX = quad.MinX + (quad.MaxX - quad.MinX) * 0.5f;
|
||||
var midY = quad.MinY + (quad.MaxY - quad.MinY) * 0.5f;
|
||||
branch.Quads[0].Set(quad.MinX, quad.MinY, midX, midY);
|
||||
branch.Quads[1].Set(midX, quad.MinY, quad.MaxX, midY);
|
||||
branch.Quads[2].Set(midX, midY, quad.MaxX, quad.MaxY);
|
||||
branch.Quads[3].Set(quad.MinX, midY, midX, quad.MaxY);
|
||||
return branch;
|
||||
}
|
||||
|
||||
private static Leaf CreateLeaf(T value, ref Quad quad)
|
||||
{
|
||||
var leaf = _leafPool.Count > 0 ? _leafPool.Pop() : new Leaf();
|
||||
leaf.Value = value;
|
||||
leaf.Quad = quad;
|
||||
return leaf;
|
||||
}
|
||||
|
||||
public class Branch
|
||||
{
|
||||
internal QuadTree<T> Tree;
|
||||
internal Branch Parent;
|
||||
internal readonly Quad[] Quads = new Quad[4];
|
||||
internal readonly Branch[] Branches = new Branch[4];
|
||||
internal readonly List<Leaf> Leaves = new List<Leaf>();
|
||||
internal bool Split;
|
||||
internal int Depth;
|
||||
|
||||
internal void Clear()
|
||||
{
|
||||
Tree = null;
|
||||
Parent = null;
|
||||
Split = false;
|
||||
|
||||
for (var i = 0; i < 4; ++i)
|
||||
{
|
||||
if (Branches[i] == null) continue;
|
||||
_branchPool.Push(Branches[i]);
|
||||
Branches[i].Clear();
|
||||
Branches[i] = null;
|
||||
}
|
||||
|
||||
foreach (var t in Leaves)
|
||||
{
|
||||
_leafPool.Push(t);
|
||||
t.Branch = null;
|
||||
t.Value = default;
|
||||
}
|
||||
|
||||
Leaves.Clear();
|
||||
}
|
||||
|
||||
internal void Insert(Leaf leaf)
|
||||
{
|
||||
//If this branch is already split
|
||||
if (Split)
|
||||
{
|
||||
for (var i = 0; i < 4; ++i)
|
||||
{
|
||||
if (!Quads[i].Contains(ref leaf.Quad)) continue;
|
||||
Branches[i] ??= CreateBranch(Tree, this, Depth + 1, ref Quads[i]);
|
||||
Branches[i].Insert(leaf);
|
||||
return;
|
||||
}
|
||||
|
||||
Leaves.Add(leaf);
|
||||
leaf.Branch = this;
|
||||
}
|
||||
else
|
||||
{
|
||||
//Add the leaf to this node
|
||||
Leaves.Add(leaf);
|
||||
leaf.Branch = this;
|
||||
|
||||
//Once I have reached capacity, split the node
|
||||
if (Leaves.Count >= Tree._splitCount && Depth < Tree._depthLimit)
|
||||
{
|
||||
Split = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
internal void SearchQuad(ref Quad quad, List<T> values)
|
||||
{
|
||||
if (Leaves.Count > 0)
|
||||
foreach (var t in Leaves)
|
||||
if (quad.Intersects(ref t.Quad))
|
||||
values.Add(t.Value);
|
||||
|
||||
for (var i = 0; i < 4; ++i)
|
||||
if (Branches[i] != null)
|
||||
Branches[i].SearchQuad(ref quad, values);
|
||||
}
|
||||
|
||||
internal void SearchPoint(float x, float y, List<T> values)
|
||||
{
|
||||
if (Leaves.Count > 0) values.AddRange(from t in Leaves where t.Quad.Contains(x, y) select t.Value);
|
||||
|
||||
for (var i = 0; i < 4; ++i)
|
||||
if (Branches[i] != null)
|
||||
Branches[i].SearchPoint(x, y, values);
|
||||
}
|
||||
}
|
||||
|
||||
internal class Leaf
|
||||
{
|
||||
internal Branch Branch;
|
||||
internal T Value;
|
||||
internal Quad Quad;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public struct Quad
|
||||
{
|
||||
public float MinX;
|
||||
public float MinY;
|
||||
public float MaxX;
|
||||
public float MaxY;
|
||||
|
||||
public Quad(float minX, float minY, float maxX, float maxY)
|
||||
{
|
||||
MinX = minX;
|
||||
MinY = minY;
|
||||
MaxX = maxX;
|
||||
MaxY = maxY;
|
||||
}
|
||||
|
||||
public void Set(float minX, float minY, float maxX, float maxY)
|
||||
{
|
||||
MinX = minX;
|
||||
MinY = minY;
|
||||
MaxX = maxX;
|
||||
MaxY = maxY;
|
||||
}
|
||||
|
||||
|
||||
public bool Intersects(ref Quad other)
|
||||
{
|
||||
return MinX < other.MaxX && MinY < other.MaxY && MaxX > other.MinX && MaxY > other.MinY;
|
||||
}
|
||||
|
||||
public bool Contains(ref Quad other)
|
||||
{
|
||||
return other.MinX >= MinX && other.MinY >= MinY && other.MaxX <= MaxX && other.MaxY <= MaxY;
|
||||
}
|
||||
|
||||
public bool Contains(float x, float y)
|
||||
{
|
||||
return x > MinX && y > MinY && x < MaxX && y < MaxY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user