From 90ef3532881a1af302d70c607c613e633deef4fd Mon Sep 17 00:00:00 2001 From: Louis Pearson Date: Tue, 18 Jan 2022 00:05:03 -0700 Subject: [PATCH] Wires can be placed into plugs --- assets/maps/map.zig | 6 +- assets/maps/test.json | 32 +++++++++- assets/maps/test.tmx | 16 +++-- src/ecs.zig | 52 ++++++++++++----- src/main.zig | 132 ++++++++++++++++++++++++++++++++++++++---- 5 files changed, 201 insertions(+), 37 deletions(-) diff --git a/assets/maps/map.zig b/assets/maps/map.zig index 3892ca5..6a79072 100644 --- a/assets/maps/map.zig +++ b/assets/maps/map.zig @@ -1,6 +1,6 @@ const std = @import("std"); const Vec2 = std.meta.Vector(2,i32); const Wire = struct { p1: Vec2, p2: Vec2, a1: bool, a2: bool }; -pub const solid: [400]u8 = .{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 50, 19, 19, 19, 19, 19, 19, 19, 19, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 65, 19, 19, 19, 19, 19, 19, 19, 19, 19, 52, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 54, 66, 52, 1, 1, 1, 51, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 33, 54, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 51, 1, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; -pub const conduit: [400]u8 = .{ 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, 131, 131, 180, 0, 0, 0, 0, 0, 0, 178, 180, 0, 0, 0, 0, 0, 0, 178, 130, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 163, 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 }; -pub const wire: [2]Wire = [_]Wire{.{.a1 = true, .a2 = true,.p1 = Vec2{ 20, 20 },.p2 = Vec2{ 76, 20 },}, .{.a1 = true, .a2 = false,.p1 = Vec2{ 84, 19 },.p2 = Vec2{ 139, 20 },}, }; +pub const solid: [400]u8 = .{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 21, 22, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 50, 19, 19, 19, 19, 19, 19, 54, 54, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 65, 19, 19, 19, 19, 19, 19, 19, 19, 19, 52, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 19, 19, 19, 52, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 54, 66, 52, 1, 1, 1, 51, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 33, 54, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 51, 1, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; +pub const conduit: [400]u8 = .{ 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, 131, 131, 180, 0, 0, 0, 0, 0, 0, 178, 180, 0, 0, 0, 0, 0, 0, 178, 130, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 147, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 163, 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 }; +pub const wire: [3]Wire = [_]Wire{.{.a1 = true, .a2 = true,.p1 = Vec2{ 20, 20 },.p2 = Vec2{ 76, 20 },}, .{.a1 = true, .a2 = false,.p1 = Vec2{ 84, 19 },.p2 = Vec2{ 139, 20 },}, .{.a1 = true, .a2 = false,.p1 = Vec2{ 60, 68 },.p2 = Vec2{ 117, 69 },}, }; diff --git a/assets/maps/test.json b/assets/maps/test.json index dc0ebf8..5494acf 100644 --- a/assets/maps/test.json +++ b/assets/maps/test.json @@ -3,7 +3,7 @@ "infinite":false, "layers":[ { - "data":[1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 50, 19, 19, 19, 19, 19, 19, 19, 19, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 65, 19, 19, 19, 19, 19, 19, 19, 19, 19, 52, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 54, 66, 52, 1, 1, 1, 51, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 33, 54, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 51, 1, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1], + "data":[1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 54, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 21, 22, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 50, 19, 19, 19, 19, 19, 19, 54, 54, 1, 1, 1, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 65, 19, 19, 19, 19, 19, 19, 19, 19, 19, 52, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 19, 19, 19, 52, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 36, 52, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 50, 67, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 1, 39, 1, 1, 1, 1, 20, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 37, 1, 54, 66, 52, 1, 1, 1, 51, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 33, 54, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 51, 1, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1], "height":20, "id":1, "name":"solid", @@ -15,7 +15,7 @@ "y":0 }, { - "data":[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, 131, 131, 180, 0, 0, 0, 0, 0, 0, 178, 180, 0, 0, 0, 0, 0, 0, 178, 130, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 163, 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], + "data":[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, 131, 131, 180, 0, 0, 0, 0, 0, 0, 178, 180, 0, 0, 0, 0, 0, 0, 178, 130, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 147, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 132, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 163, 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], "height":20, "id":2, "name":"conduit", @@ -76,6 +76,32 @@ "width":0, "x":84.125, "y":19.875 + }, + { + "height":0, + "id":7, + "name":"", + "polyline":[ + { + "x":0, + "y":0 + }, + { + "x":57.2727272727273, + "y":1.27272727272727 + }], + "properties":[ + { + "name":"anchor2", + "type":"bool", + "value":false + }], + "rotation":0, + "type":"wire", + "visible":true, + "width":0, + "x":60, + "y":68.1818181818182 }], "opacity":1, "type":"objectgroup", @@ -84,7 +110,7 @@ "y":0 }], "nextlayerid":4, - "nextobjectid":7, + "nextobjectid":8, "orientation":"orthogonal", "renderorder":"right-down", "tiledversion":"1.7.2", diff --git a/assets/maps/test.tmx b/assets/maps/test.tmx index c2281a9..f1d028b 100644 --- a/assets/maps/test.tmx +++ b/assets/maps/test.tmx @@ -1,5 +1,5 @@ - + @@ -9,13 +9,13 @@ 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, 1,1,54,54,54,54,54,54,54,54,54,54,54,54,54,54,54,54,1,1, 1,39,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,37,1, -1,39,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,37,1, -1,39,1,1,1,1,1,1,1,50,19,19,19,19,19,19,19,19,1,1, +1,39,1,1,1,1,1,1,1,1,1,1,1,1,1,1,21,22,1,1, +1,39,1,1,1,1,1,1,1,50,19,19,19,19,19,19,54,54,1,1, 1,39,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,37,1, 1,39,1,1,1,50,65,19,19,19,19,19,19,19,19,19,52,1,37,1, 1,39,1,1,1,1,20,1,1,1,1,1,1,1,1,1,1,1,37,1, 1,36,52,1,1,1,20,1,1,1,1,1,1,1,1,1,1,1,37,1, -1,39,1,1,1,1,20,1,1,1,1,1,1,1,1,1,1,1,37,1, +1,39,1,1,1,1,20,19,19,19,52,1,1,1,1,1,1,1,37,1, 1,39,1,1,1,50,67,1,1,1,1,1,1,1,1,1,1,1,37,1, 1,39,1,1,1,1,20,1,1,1,1,1,1,1,1,1,1,1,37,1, 1,36,52,1,1,1,20,1,1,1,1,1,1,1,1,1,1,1,37,1, @@ -38,7 +38,7 @@ 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, -0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, +0,0,0,0,0,0,0,147,0,0,0,0,0,0,0,0,0,0,132,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,132,0, @@ -62,5 +62,11 @@ + + + + + + diff --git a/src/ecs.zig b/src/ecs.zig index 43517eb..1e5bec7 100644 --- a/src/ecs.zig +++ b/src/ecs.zig @@ -53,17 +53,17 @@ pub fn World(comptime ComponentBase: type) type { return this; } - pub fn require(set: []const ComponentEnum) @This() { + pub fn require(require_set: []const ComponentEnum) @This() { var this = @This(){}; - for (set) |f| { + for (require_set) |f| { this.required.insert(f); } return this; } - pub fn exclude(set: []const ComponentEnum) @This() { + pub fn exclude(exclude_set: []const ComponentEnum) @This() { var this = @This(){}; - for (set) |f| { + for (exclude_set) |f| { this.excluded.insert(f); } return this; @@ -92,8 +92,13 @@ pub fn World(comptime ComponentBase: type) type { @compileError("unimplemented"); } - pub fn get(this: *@This(), entity: usize, comptime component: ComponentEnum) *Component { - return this.components.items(component)[entity]; + /// Returns a copy of the components on an entity + pub fn get(this: *@This(), entity: usize) Component { + return this.components.get(entity); + } + + pub fn set(this: *@This(), entity: usize, component: Component) void { + this.components.set(entity, component); } fn enum2type(comptime enumList: []const ComponentEnum) []type { @@ -108,13 +113,31 @@ pub fn World(comptime ComponentBase: type) type { pub fn process(this: *@This(), dt: f32, comptime comp: []const ComponentEnum, func: anytype) void { const Args = Tuple([_]type{f32} ++ enum2type(comp)); var i = this.iter(Query.require(comp)); - while (i.next()) |e| { + while (i.next()) |eID| { + var e = this.get(eID); var args: Args = undefined; args[0] = dt; inline for (comp) |f, j| { args[j + 1] = &(@field(e, @tagName(f)).?); } @call(.{}, func, args); + this.set(eID, e); + } + } + + pub fn processWithID(this: *@This(), dt: f32, comptime comp: []const ComponentEnum, func: anytype) void { + const Args = Tuple([_]type{ f32, usize } ++ enum2type(comp)); + var i = this.iter(Query.require(comp)); + while (i.next()) |eID| { + var e = this.get(eID); + var args: Args = undefined; + args[0] = dt; + args[1] = eID; + inline for (comp) |f, j| { + args[j + 2] = &(@field(e, @tagName(f)).?); + } + @call(.{}, func, args); + this.set(eID, e); } } @@ -129,40 +152,41 @@ pub fn World(comptime ComponentBase: type) type { const Self = @This(); const Iterator = struct { world: *Self, - lastComponent: ?Component, + // lastIndex: ?usize, index: usize, query: ComponentQuery, pub fn init(w: *Self, q: ComponentQuery) @This() { return @This(){ .world = w, - .lastComponent = null, + // .lastComponent = null, .index = 0, .query = q, }; } - pub fn next(this: *@This()) ?*Component { - if (this.lastComponent) |e| this.world.components.set(this.index - 1, e); + pub fn next(this: *@This()) ?usize { + // if (this.lastIndex) |_| this.index += 1; if (this.index == this.world.components.len) return null; var match = false; while (!match) { if (this.index == this.world.components.len) return null; - this.lastComponent = this.world.components.get(this.index); + const e = this.world.components.get(this.index); match = true; inline for (fields) |f| { const fenum = std.meta.stringToEnum(ComponentEnum, f.name) orelse unreachable; const required = this.query.required.contains(fenum); const excluded = this.query.excluded.contains(fenum); - const has = @field(this.lastComponent.?, f.name) != null; + const has = @field(e, f.name) != null; if ((required and !has) or (excluded and has)) { match = false; break; } } this.index += 1; + if (match) return this.index - 1; } - return &this.lastComponent.?; + return null; } }; }; diff --git a/src/main.zig b/src/main.zig index 416945e..6138ae7 100644 --- a/src/main.zig +++ b/src/main.zig @@ -68,12 +68,13 @@ const Control = struct { controller: enum { player }, state: enum { stand, walk, jump, fall, wallSlide }, facing: enum { left, right } = .right, + grabbing: ?struct { id: usize, which: usize } = null, }; const Sprite = struct { offset: Vec2f = Vec2f{ 0, 0 }, size: w4.Vec2, index: usize, flags: w4.BlitFlags }; const StaticAnim = Anim; const ControlAnim = struct { anims: []AnimData, state: Anim }; const Kinematic = struct { col: AABB, move: Vec2f = Vec2f{ 0, 0 }, lastCol: Vec2f = Vec2f{ 0, 0 } }; -const Wire = struct { nodes: std.BoundedArray(Pos, 10), anchored: [2]?enum { stationary, grabbed } = null }; +const Wire = struct { nodes: std.BoundedArray(Pos, 32), anchored: [2]?union(enum) { stationary, grabbed: u32 } = null }; const Physics = struct { gravity: Vec2f, friction: Vec2f }; const Component = struct { pos: Pos, @@ -136,10 +137,12 @@ export fn start() void { const end = vec2tovec2f(wire.p2); const size = end - begin; - var nodes = std.BoundedArray(Pos, 10).init(0) catch showErr("Nodes"); + var nodes = std.BoundedArray(Pos, 32).init(0) catch showErr("Nodes"); var i: usize = 0; - while (i <= 5) : (i += 1) { - const pos = begin + @splat(2, @intToFloat(f32, i)) * size / @splat(2, @as(f32, 5)); + const divisions = @floatToInt(usize, length(size) / wireSegmentMaxLength); + w4.trace("{d:.0} long, {} divisions", .{ length(size), divisions }); + while (i <= divisions) : (i += 1) { + const pos = begin + @splat(2, @intToFloat(f32, i)) * size / @splat(2, @intToFloat(f32, divisions)); nodes.append(Pos.init(pos)) catch showErr("Appending nodes"); } const w = Wire{ .nodes = nodes, .anchored = .{ if (wire.a1) .stationary else null, if (wire.a2) .stationary else null } }; @@ -149,12 +152,15 @@ export fn start() void { } } +var indicator: ?Vec2 = null; + export fn update() void { w4.DRAW_COLORS.* = 0x0004; w4.rect(.{ 0, 0 }, .{ 160, 160 }); world.process(1, &.{.pos}, velocityProcess); world.process(1, &.{ .pos, .physics }, physicsProcess); + world.processWithID(1, &.{ .pos, .control }, wireManipulationProcess); world.process(1, &.{.wire}, wirePhysicsProcess); world.process(1, &.{ .pos, .control, .physics, .kinematic }, controlProcess); world.process(1, &.{ .pos, .kinematic }, kinematicProcess); @@ -177,9 +183,84 @@ export fn update() void { } world.process(1, &.{.wire}, wireDrawProcess); + + if (indicator) |pos| { + w4.oval(pos - w4.Vec2{ 2, 2 }, w4.Vec2{ 5, 5 }); + } + + indicator = null; input.update(); } +fn is_plug(tile: u8) bool { + return tile == 176 or tile == 177 or tile == 178 or tile == 179 or tile == 146; +} + +/// pos should be in tile coordinates, not world coordinates +fn get_conduit(vec: Vec2) ?u8 { + const x = vec[0]; + const y = vec[1]; + if (x < 0 or x > 19 or y < 0 or y > 19) return null; + const i = x + y * 20; + return assets.conduit[@intCast(u32, i)]; +} + +fn wireManipulationProcess(_: f32, id: usize, pos: *Pos, control: *Control) void { + if (control.grabbing) |details| { + var offset = if (control.facing == .left) Vec2f{ -6, -4 } else Vec2f{ 6, -4 }; + var mapPos = vec2ftovec2((pos.pos + offset) / @splat(2, @as(f32, 8))); + if (is_plug(get_conduit(mapPos) orelse 0)) { + indicator = mapPos * @splat(2, @as(i32, 8)) + Vec2{ 4, 4 }; + if (input.btnp(.one, .two)) { + var e = world.get(details.id); + e.wire.?.anchored[details.which] = .stationary; + e.wire.?.nodes.slice()[e.wire.?.nodes.len - 1].pos = vec2tovec2f(indicator.?); + world.set(details.id, e); + control.grabbing = null; + } + } else if (input.btnp(.one, .two)) { + var e = world.get(details.id); + e.wire.?.anchored[details.which] = null; + world.set(details.id, e); + control.grabbing = null; + } + } else { + const interactDistance = 8; + var minDistance: f32 = interactDistance; + var wireIter = world.iter(World.Query.require(&.{.wire})); + var interactWireID: ?usize = null; + var which: usize = 0; + while (wireIter.next()) |entityID| { + const entity = world.get(entityID); + const wire = entity.wire.?; + const nodes = wire.nodes.constSlice(); + const begin = nodes[0].pos; + const end = nodes[wire.nodes.len - 1].pos; + var beginDist = distancef(begin, pos.pos); + var endDist = distancef(end, pos.pos); + if (beginDist < minDistance) { + minDistance = beginDist; + indicator = vec2ftovec2(begin); + interactWireID = entityID; + which = 0; + } else if (endDist < minDistance) { + minDistance = endDist; + indicator = vec2ftovec2(end); + interactWireID = entityID; + which = 1; + } + } + if (interactWireID) |wireID| { + var entity = world.get(wireID); + if (input.btnp(.one, .two)) { + control.grabbing = .{ .id = wireID, .which = which }; + entity.wire.?.anchored[which] = .{ .grabbed = id }; + } + world.set(wireID, entity); + } + } +} + fn distance(a: w4.Vec2, b: w4.Vec2) i32 { var subbed = a - b; subbed[0] = std.math.absInt(subbed[0]) catch unreachable; @@ -219,8 +300,30 @@ fn wirePhysicsProcess(dt: f32, wire: *Wire) void { collideNode(node); } - if (wire.anchored[0] != null) nodes[0].pos = nodes[0].last; - if (wire.anchored[1] != null) nodes[nodes.len - 1].pos = nodes[nodes.len - 1].last; + if (wire.anchored[0]) |anchor| { + switch (anchor) { + .stationary => nodes[0].pos = nodes[0].last, + .grabbed => |grabbedBy| { + var entity = world.get(grabbedBy); + // TODO: stop player from pulling the wire through terrain + // constrainNodes(&entity.pos.?, &nodes[0]); + // world.set(grabbedBy, entity); + nodes[0].pos = entity.pos.?.pos + Vec2f{ 0, -6 }; + }, + } + } + if (wire.anchored[1]) |anchor| { + switch (anchor) { + .stationary => nodes[nodes.len - 1].pos = nodes[nodes.len - 1].last, + .grabbed => |grabbedBy| { + var entity = world.get(grabbedBy); + // TODO: stop player from pulling the wire through terrain + // constrainNodes(&entity.pos.?, &nodes[nodes.len - 1]); + // world.set(grabbedBy, entity); + nodes[nodes.len - 1].pos = entity.pos.?.pos + Vec2f{ 0, -6 }; + }, + } + } if (wire.anchored[0] != null and wire.anchored[1] != null) { var i: usize = 0; @@ -266,6 +369,10 @@ fn wirePhysicsProcess(dt: f32, wire: *Wire) void { } } } + + for (nodes) |*node| { + collideNode(node); + } } fn collideNode(node: *Pos) void { @@ -274,8 +381,6 @@ fn collideNode(node: *Pos) void { const iPos = vec2ftovec2(node.pos); const mapPos = @divTrunc(iPos, tileSize); if (is_solid(mapPos)) { - // w4.DRAW_COLORS.* = 0x0011; - // w4.rect(mapPos * tileSize, tileSize); const velNorm = normalize(node.pos - node.last); var collideVec = node.last; while (!is_solid(vec2ftovec2((collideVec + velNorm) / tileSizef))) { @@ -285,12 +390,15 @@ fn collideNode(node: *Pos) void { } } +const wireSegmentMinLength = 3; +const wireSegmentMaxLength = 6; +const wireSegmentMaxLengthV = @splat(2, @as(f32, wireSegmentMaxLength)); + fn constrainToAnchor(anchor: *Pos, node: *Pos) void { var diff = anchor.pos - node.pos; var dist = distancef(node.pos, anchor.pos); - if (dist > 8) { - node.pos = anchor.pos - (normalize(diff) * @splat(2, @as(f32, 8))); - } + var wireLength = @maximum(wireSegmentMinLength, dist); + node.pos = anchor.pos - (normalize(diff) * @splat(2, @as(f32, wireLength))); } fn constrainNodes(prevNode: *Pos, node: *Pos) void { @@ -298,7 +406,7 @@ fn constrainNodes(prevNode: *Pos, node: *Pos) void { var dist = distancef(node.pos, prevNode.pos); var difference: f32 = 0; if (dist > 0) { - difference = (8 - dist) / dist; + difference = (@minimum(dist, wireSegmentMinLength) - dist) / dist; } var translate = diff * @splat(2, 0.5 * difference); prevNode.pos += translate;