added block breaking

This commit is contained in:
MasterGordon 2022-11-09 17:50:34 +01:00
parent 03610b157d
commit 2742e0100c
16 changed files with 176 additions and 40 deletions

BIN
assets/breaking.ase Normal file

Binary file not shown.

BIN
assets/breaking.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 280 B

View File

@ -0,0 +1,25 @@
[Interactor]
class Breaking
{
[Interaction(InteractorKind.Hybrid, "tick")]
public static void TickHybrid(TickPacket packet)
{
var ctx = Context.Get();
ctx.GameState.Players.ForEach(player =>
{
Math.Max(0, player.MiningCooldown -= 1);
if (player.Mining != null && player.MiningCooldown == 0)
{
var chunk = ctx.GameState.World.GetChunkAt(player.Mining);
// chunk.SetTileAt(player.Mining, tile with { Hits = tile.Hits + 1 });
// var tile = chunk.GetTileAt(amp);
// if (tile.Hits >= hardness)
// {
// chunk.SetTileAt(amp, STile.From(0));
// }
}
}
);
}
}

View File

@ -4,9 +4,8 @@ class Bootstrapper
{ {
var ctx = Context.Get(); var ctx = Context.Get();
ctx.GameState.World = new World(); ctx.GameState.World = new World();
ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(0, 1, Tiles.stone)); ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(0, 1, STile.From(Tiles.stone)));
ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(-1, 1, Tiles.stone)); ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(1, 1, STile.From(Tiles.stone)));
ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(1, 1, Tiles.stone)); ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(1, 0, STile.From(Tiles.stone)));
ctx.GameState.World.AddChunk(ChunkGenerator.CreateFilledChunk(1, 0, Tiles.stone));
} }
} }

View File

@ -9,7 +9,6 @@ class Camera
public void CenterOn(Vector2 target) public void CenterOn(Vector2 target)
{ {
Console.WriteLine("Centering camera on " + target);
var ctx = Context.Get(); var ctx = Context.Get();
var scale = ctx.FrontendGameState.Settings.GameScale; var scale = ctx.FrontendGameState.Settings.GameScale;
var windowWidth = ctx.FrontendGameState.WindowWidth; var windowWidth = ctx.FrontendGameState.WindowWidth;

View File

@ -53,17 +53,24 @@ class PlayerEntity
hasCollision = hasCollision =
world.HasChunkAt(pL) && world.GetChunkAt(pL).hasTileAt(pL) world.HasChunkAt(pL) && world.GetChunkAt(pL).hasTileAt(pL)
|| world.HasChunkAt(pR) && world.GetChunkAt(pR).hasTileAt(pR); || world.HasChunkAt(pR) && world.GetChunkAt(pR).hasTileAt(pR);
Console.WriteLine(World.ToChunkPos(p.Position));
if (world.HasChunkAt(p.Position))
{
var chunk = world.GetChunkAt(p.Position);
Console.WriteLine($"Chunk: {chunk.X}, {chunk.Y}");
}
if (hasCollision) if (hasCollision)
{ {
p.Movement = p.Movement with { Y = 0 }; p.Movement = p.Movement with { Y = 0 };
p.Position += new Vector2(0, -0.1f); p.Position += new Vector2(0, -0.1f);
} }
} while (hasCollision); } while (hasCollision);
do
{
var pL = p.Position + new Vector2(0, -32);
var pR = p.Position + new Vector2(16, -32);
hasCollision =
world.HasChunkAt(pL) && world.GetChunkAt(pL).hasTileAt(pL)
|| world.HasChunkAt(pR) && world.GetChunkAt(pR).hasTileAt(pR);
if (hasCollision)
{
p.Movement = p.Movement with { Y = 0 };
p.Position += new Vector2(0, 0.1f);
}
} while (hasCollision);
} }
} }

View File

@ -1,6 +1,6 @@
class Chunk class Chunk
{ {
public int[,] Tiles { get; set; } = new int[Constants.ChunkSize, Constants.ChunkSize]; public STile[,] Tiles { get; set; } = new STile[Constants.ChunkSize, Constants.ChunkSize];
public int X { get; set; } public int X { get; set; }
public int Y { get; set; } public int Y { get; set; }
@ -10,12 +10,12 @@ class Chunk
this.Y = y; this.Y = y;
} }
public void SetTile(int x, int y, int tile) public void SetTile(int x, int y, STile tile)
{ {
this.Tiles[x, y] = tile; this.Tiles[x, y] = tile;
} }
public int GetTile(int x, int y) public STile GetTile(int x, int y)
{ {
return this.Tiles[x, y]; return this.Tiles[x, y];
} }
@ -33,21 +33,35 @@ class Chunk
return this.hasTile(tileX, tileY); return this.hasTile(tileX, tileY);
} }
public int GetTileAt(Vector2 pos) public STile GetTileAt(Vector2 pos)
{ {
return this.GetTileAt((int)pos.X, (int)pos.Y); return this.GetTileAt((int)pos.X, (int)pos.Y);
} }
public int GetTileAt(int x, int y) public STile GetTileAt(int x, int y)
{ {
var tileX = (int)Math.Floor(x / (float)Constants.TileSize); var posInChunk = this.GetPositionInChunk(new Vector2(x, y));
var tileY = (int)Math.Floor(y / (float)Constants.TileSize); var tileX = (int)Math.Floor(posInChunk.X / Constants.TileSize);
var tileY = (int)Math.Floor(posInChunk.Y / Constants.TileSize);
return this.GetTile(tileX, tileY); return this.GetTile(tileX, tileY);
} }
public void SetTileAt(Vector2 pos, STile tile)
{
this.SetTileAt((int)pos.X, (int)pos.Y, tile);
}
public void SetTileAt(int x, int y, STile tile)
{
var posInChunk = this.GetPositionInChunk(new Vector2(x, y));
var tileX = (int)Math.Floor(posInChunk.X / Constants.TileSize);
var tileY = (int)Math.Floor(posInChunk.Y / Constants.TileSize);
this.SetTile(tileX, tileY, tile);
}
public bool hasTile(int x, int y) public bool hasTile(int x, int y)
{ {
return x >= 0 && x < this.Tiles.Length && y >= 0 && y < this.Tiles.Length; return x >= 0 && x < this.Tiles.Length && y >= 0 && y < this.Tiles.Length && this.Tiles[x, y].Id != 0;
} }
public bool hasTile(Vector2 pos) public bool hasTile(Vector2 pos)

18
src/core/data/STile.cs Normal file
View File

@ -0,0 +1,18 @@
struct STile
{
public int Id { get; set; }
public int Hits { get; set; }
public static STile From(int id)
{
return new STile()
{
Id = id
};
}
public static STile From(Tiles id)
{
return From((int)id);
}
}

View File

@ -63,11 +63,16 @@ class World
return new Vector2((float)chunkX, (float)chunkY); return new Vector2((float)chunkX, (float)chunkY);
} }
public int GetTileAt(int x, int y) public STile GetTileAt(int x, int y)
{ {
return this.GetChunkAt(x, y).GetTileAt(x, y); return this.GetChunkAt(x, y).GetTileAt(x, y);
} }
public void SetTileAt(int x, int y, STile tile)
{
this.GetChunkAt(x, y).SetTileAt(x, y, tile);
}
public bool HasTileAt(int x, int y) public bool HasTileAt(int x, int y)
{ {
return this.HasChunkAt(x, y) && this.GetChunkAt(x, y).hasTileAt(new Vector2(x, y)); return this.HasChunkAt(x, y) && this.GetChunkAt(x, y).hasTileAt(new Vector2(x, y));

View File

View File

@ -1,37 +1,68 @@
class Tile class Tile
{ {
public string Name { get; set; } public string Name { get; set; }
public IntPtr Texture { get; set; } public int Hardness { get; set; }
private readonly IntPtr texture;
private static IntPtr breakingTexture;
public Tile(string name, string textureName) public Tile(string name, string textureName, int hardness)
{ {
this.Name = name; this.Name = name;
this.Hardness = hardness;
var rl = Context.Get().ResourceLoader; var rl = Context.Get().ResourceLoader;
var (ptr, size) = rl.LoadToIntPtr("assets." + textureName + ".png"); var (ptr, size) = rl.LoadToIntPtr("assets." + textureName + ".png");
var sdlBuffer = SDL_RWFromMem(ptr, size); var sdlBuffer = SDL_RWFromMem(ptr, size);
var surface = IMG_Load_RW(sdlBuffer, 1); var surface = IMG_Load_RW(sdlBuffer, 1);
var texture = Context.Get().Renderer.CreateTextureFromSurface(surface); var texture = Context.Get().Renderer.CreateTextureFromSurface(surface);
this.Texture = texture; this.texture = texture;
if (breakingTexture == IntPtr.Zero)
{
loadBreakingTexture();
}
SDL_FreeSurface(surface); SDL_FreeSurface(surface);
} }
~Tile() ~Tile()
{ {
SDL_DestroyTexture(this.Texture); SDL_DestroyTexture(this.texture);
} }
public void Render(int x, int y) public void Render(int x, int y, STile tile)
{ {
var renderer = Context.Get().Renderer; var renderer = Context.Get().Renderer;
var scale = Context.Get().FrontendGameState.Settings.GameScale; var scale = Context.Get().FrontendGameState.Settings.GameScale;
var camera = Context.Get().FrontendGameState.Camera; var camera = Context.Get().FrontendGameState.Camera;
renderer.DrawTexture( renderer.DrawTexture(
this.Texture, this.texture,
(x - (int)camera.position.X) * scale, (x - (int)camera.position.X) * scale,
(y - (int)camera.position.Y) * scale, (y - (int)camera.position.Y) * scale,
Constants.TileSize * scale, Constants.TileSize * scale,
Constants.TileSize * scale Constants.TileSize * scale
); );
if (tile.Hits > 0)
{
var breakingOffset = (int)((double)tile.Hits / this.Hardness * 4);
renderer.DrawTexture(
breakingTexture,
(x - (int)camera.position.X) * scale,
(y - (int)camera.position.Y) * scale,
Constants.TileSize * scale,
Constants.TileSize * scale,
breakingOffset,
16,
16
);
}
}
private static void loadBreakingTexture()
{
var rl = Context.Get().ResourceLoader;
var (ptr, size) = rl.LoadToIntPtr("assets.breaking.png");
var sdlBuffer = SDL_RWFromMem(ptr, size);
var surface = IMG_Load_RW(sdlBuffer, 1);
breakingTexture = Context.Get().Renderer.CreateTextureFromSurface(surface);
SDL_FreeSurface(surface);
} }
} }

View File

@ -9,7 +9,7 @@ class TileRegistry
public void RegisterTile() public void RegisterTile()
{ {
this.Tiles.Add(1, new Tile("stone", "stone")); this.Tiles.Add(1, new Tile("stone", "stone", 5));
} }
public Tile GetTile(int id) public Tile GetTile(int id)

View File

@ -1,6 +1,6 @@
class ChunkGenerator class ChunkGenerator
{ {
public static Chunk CreateFilledChunk(int x, int y, int fill) public static Chunk CreateFilledChunk(int x, int y, STile fill)
{ {
var chunk = new Chunk(x, y); var chunk = new Chunk(x, y);
for (var i = 0; i < Constants.ChunkSize; i++) for (var i = 0; i < Constants.ChunkSize; i++)
@ -12,9 +12,4 @@ class ChunkGenerator
} }
return chunk; return chunk;
} }
public static Chunk CreateFilledChunk(int x, int y, Tiles fill)
{
return CreateFilledChunk(x, y, (int)fill);
}
} }

View File

@ -128,6 +128,25 @@ class Renderer
w = w, w = w,
h = h h = h
}; };
SDL_RenderCopy(renderer, texture, IntPtr.Zero, ref rect); _ = SDL_RenderCopy(this.renderer, texture, IntPtr.Zero, ref rect);
}
public void DrawTexture(IntPtr texture, int x, int y, int w, int h, int offsetIndex, int srcWidth, int srcHeight)
{
SDL_Rect rect = new()
{
x = x,
y = y,
w = w,
h = h
};
SDL_Rect srcRect = new()
{
x = srcWidth * offsetIndex,
y = 0,
w = srcWidth,
h = srcHeight,
};
_ = SDL_RenderCopy(this.renderer, texture, ref srcRect, ref rect);
} }
} }

View File

@ -42,6 +42,26 @@ class Frontend : IFrontend
Console.WriteLine($"Mouse moved to {mousePos}"); Console.WriteLine($"Mouse moved to {mousePos}");
ctx.FrontendGameState.MousePosition = mousePos; ctx.FrontendGameState.MousePosition = mousePos;
} }
if (e.type == SDL_EventType.SDL_MOUSEBUTTONDOWN && e.button.button == SDL_BUTTON_LEFT)
{
var amp = ctx.FrontendGameState.MousePosition / ctx.FrontendGameState.Settings.GameScale + ctx.FrontendGameState.Camera.position;
if (ctx.GameState.World.HasChunkAt(amp))
{
var chunk = ctx.GameState.World.GetChunkAt(amp);
var tile = chunk.GetTileAt(amp);
var tileId = tile.Id;
if (tile.Id != 0)
{
var tileRegistry = ctx.TileRegistry;
var hardness = tileRegistry.GetTile(tileId).Hardness;
chunk.SetTileAt(amp, tile with { Hits = tile.Hits + 1 });
if (tile.Hits >= hardness)
{
chunk.SetTileAt(amp, STile.From(0));
}
}
}
}
if (e.type == SDL_EventType.SDL_KEYDOWN && e.key.repeat == 0) if (e.type == SDL_EventType.SDL_KEYDOWN && e.key.repeat == 0)
{ {
var movementInput = ctx.FrontendGameState.MovementInput; var movementInput = ctx.FrontendGameState.MovementInput;

View File

@ -4,19 +4,23 @@ class WorldRenderer : IRenderer
{ {
var ctx = Context.Get(); var ctx = Context.Get();
var world = ctx.GameState.World; var world = ctx.GameState.World;
var renderer = ctx.Renderer;
var tileRegistry = ctx.TileRegistry; var tileRegistry = ctx.TileRegistry;
foreach (var (_, chunk) in world.Chunks) foreach (var (_, chunk) in world.Chunks)
{ {
for (int y = 0; y < Constants.ChunkSize; y++) for (var y = 0; y < Constants.ChunkSize; y++)
{ {
for (int x = 0; x < Constants.ChunkSize; x++) for (var x = 0; x < Constants.ChunkSize; x++)
{ {
var tileId = chunk.GetTile(x, y); var stile = chunk.GetTile(x, y);
var tile = tileRegistry.GetTile(tileId); if (stile.Id == 0)
{
continue;
}
var tile = tileRegistry.GetTile(stile.Id);
var chunkOffsetX = chunk.X * Constants.TileSize * Constants.ChunkSize; var chunkOffsetX = chunk.X * Constants.TileSize * Constants.ChunkSize;
var chunkOffsetY = chunk.Y * Constants.TileSize * Constants.ChunkSize; var chunkOffsetY = chunk.Y * Constants.TileSize * Constants.ChunkSize;
tile.Render(x * 16 + chunkOffsetX, y * 16 + chunkOffsetY); tile.Render(x * 16 + chunkOffsetX, y * 16 + chunkOffsetY, stile);
} }
} }
} }