bevy-learning

A learning project of mine.
git clone git://archive.git.mtrnord.blog/MTRNord/bevy-learning.git
Log | Files | Refs

commit 84043789f5438f0c62589b1f77d53f8ed118e55e
parent e242e1cbcbbb450814ef43b95e064f1d93eb3a25
Author: MTRNord <mtrnord1@gmail.com>
Date:   Wed, 31 Mar 2021 22:35:04 +0200

Fix map gen and add grid movement

Took 3 hours 27 minutes

Diffstat:
MCargo.lock | 123++++++++++++++++++++++++++++++++++++++++++++++++++++++++++---------------------
MCargo.toml | 2+-
Msrc/entities/common.rs | 2+-
Msrc/entities/markers.rs | 5+++++
Msrc/entities/player.rs | 2+-
Msrc/main.rs | 26++++++++++++--------------
Msrc/plugins/mod.rs | 2+-
Msrc/plugins/player.rs | 313++++++++++++++++++++++++++++++++-----------------------------------------------
Msrc/plugins/world.rs | 178++++++++++++++++++++++++++++++++++++++++++++-----------------------------------
9 files changed, 339 insertions(+), 314 deletions(-)

diff --git a/Cargo.lock b/Cargo.lock @@ -244,7 +244,7 @@ checksum = "904dfeac50f3cdaba28fc6f57fdcddb75f49ed61346676a78c4ffe55877802fd" [[package]] name = "bevy" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_dylib", "bevy_internal", @@ -275,7 +275,7 @@ dependencies = [ [[package]] name = "bevy_app" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_derive 0.4.0", "bevy_ecs 0.4.0", @@ -318,7 +318,7 @@ dependencies = [ [[package]] name = "bevy_asset" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "anyhow", "bevy_app 0.4.0", @@ -346,7 +346,7 @@ dependencies = [ [[package]] name = "bevy_audio" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "anyhow", "bevy_app 0.4.0", @@ -361,7 +361,7 @@ dependencies = [ [[package]] name = "bevy_core" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_derive 0.4.0", @@ -389,7 +389,7 @@ dependencies = [ [[package]] name = "bevy_derive" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "Inflector", "find-crate", @@ -401,7 +401,7 @@ dependencies = [ [[package]] name = "bevy_diagnostic" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_core", @@ -428,7 +428,7 @@ dependencies = [ [[package]] name = "bevy_dylib" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_internal", ] @@ -436,7 +436,7 @@ dependencies = [ [[package]] name = "bevy_dynamic_plugin" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "libloading 0.7.0", @@ -462,7 +462,7 @@ dependencies = [ [[package]] name = "bevy_ecs" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "async-channel", "bevy_ecs_macros", @@ -482,7 +482,7 @@ dependencies = [ [[package]] name = "bevy_ecs_macros" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "find-crate", "proc-macro2", @@ -493,7 +493,7 @@ dependencies = [ [[package]] name = "bevy_gilrs" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_ecs 0.4.0", @@ -505,7 +505,7 @@ dependencies = [ [[package]] name = "bevy_gltf" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "anyhow", "base64", @@ -550,7 +550,7 @@ dependencies = [ [[package]] name = "bevy_input" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_ecs 0.4.0", @@ -561,7 +561,7 @@ dependencies = [ [[package]] name = "bevy_internal" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_asset 0.4.0", @@ -608,7 +608,7 @@ dependencies = [ [[package]] name = "bevy_log" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "android_log-sys 0.2.0", "bevy_app 0.4.0", @@ -630,7 +630,7 @@ dependencies = [ [[package]] name = "bevy_math" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_reflect", "glam 0.12.0", @@ -639,7 +639,7 @@ dependencies = [ [[package]] name = "bevy_pbr" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_asset 0.4.0", @@ -698,7 +698,7 @@ dependencies = [ [[package]] name = "bevy_reflect" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_ecs 0.4.0", @@ -716,7 +716,7 @@ dependencies = [ [[package]] name = "bevy_reflect_derive" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "find-crate", "proc-macro2", @@ -728,7 +728,7 @@ dependencies = [ [[package]] name = "bevy_render" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "anyhow", "bevy-glsl-to-spirv", @@ -759,7 +759,7 @@ dependencies = [ [[package]] name = "bevy_scene" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "anyhow", "bevy_app 0.4.0", @@ -778,7 +778,7 @@ dependencies = [ [[package]] name = "bevy_sprite" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_asset 0.4.0", @@ -813,7 +813,7 @@ dependencies = [ [[package]] name = "bevy_tasks" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "async-channel", "async-executor", @@ -827,7 +827,7 @@ dependencies = [ [[package]] name = "bevy_text" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "ab_glyph", "anyhow", @@ -849,7 +849,7 @@ dependencies = [ [[package]] name = "bevy_transform" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_ecs 0.4.0", @@ -878,7 +878,7 @@ dependencies = [ [[package]] name = "bevy_ui" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_asset 0.4.0", @@ -913,7 +913,7 @@ dependencies = [ [[package]] name = "bevy_utils" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "ahash 0.7.2", "getrandom 0.2.2", @@ -925,7 +925,7 @@ dependencies = [ [[package]] name = "bevy_wgpu" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_asset 0.4.0", @@ -946,7 +946,7 @@ dependencies = [ [[package]] name = "bevy_window" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_ecs 0.4.0", @@ -958,7 +958,7 @@ dependencies = [ [[package]] name = "bevy_winit" version = "0.4.0" -source = "git+https://github.com/bevyengine/bevy.git?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" +source = "git+https://github.com/bevyengine/bevy?rev=079b3ade89195ef1aa4bcf1f8c0740a6572b84b6#079b3ade89195ef1aa4bcf1f8c0740a6572b84b6" dependencies = [ "bevy_app 0.4.0", "bevy_ecs 0.4.0", @@ -1973,6 +1973,16 @@ dependencies = [ ] [[package]] +name = "gif" +version = "0.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "02efba560f227847cb41463a7395c514d127d4f74fff12ef0137fff1b84b96c4" +dependencies = [ + "color_quant", + "weezl", +] + +[[package]] name = "gilrs" version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -2220,11 +2230,14 @@ dependencies = [ "bytemuck", "byteorder", "color_quant", + "gif", + "jpeg-decoder", "num-iter", "num-rational", "num-traits", "png", "scoped_threadpool", + "tiff", ] [[package]] @@ -2350,6 +2363,15 @@ dependencies = [ ] [[package]] +name = "jpeg-decoder" +version = "0.1.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "229d53d58899083193af11e15917b5640cd40b29ff475a1fe4ef725deb02d0f2" +dependencies = [ + "rayon", +] + +[[package]] name = "js-sys" version = "0.3.46" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -2764,6 +2786,17 @@ dependencies = [ ] [[package]] +name = "noise" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "82051dd6745d5184c6efb7bc8be14892a7f6d4f3ad6dbf754d1c7d7d5fe24b43" +dependencies = [ + "image", + "rand 0.7.3", + "rand_xorshift", +] + +[[package]] name = "nom" version = "5.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -3171,6 +3204,15 @@ dependencies = [ ] [[package]] +name = "rand_xorshift" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77d416b86801d23dde1aa643023b775c3a462efc0ed96443add11546cdf1dca8" +dependencies = [ + "rand_core 0.5.1", +] + +[[package]] name = "range-alloc" version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -3702,6 +3744,17 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7572415bd688d401c52f6e36f4c8e805b9ae1622619303b9fa835d531db0acae" [[package]] +name = "tiff" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9a53f4706d65497df0c4349241deddf35f84cee19c87ed86ea8ca590f4464437" +dependencies = [ + "jpeg-decoder", + "miniz_oxide 0.4.4", + "weezl", +] + +[[package]] name = "time" version = "0.2.26" source = "registry+https://github.com/rust-lang/crates.io-index" @@ -3863,7 +3916,7 @@ dependencies = [ "bevy_discovery", "bevy_ldtk", "bevy_prototype_inline_assets", - "rayon", + "noise", ] [[package]] @@ -4101,6 +4154,12 @@ dependencies = [ ] [[package]] +name = "weezl" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4a32b378380f4e9869b22f0b5177c68a5519f03b3454fde0b291455ddbae266c" + +[[package]] name = "wgpu" version = "0.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" diff --git a/Cargo.toml b/Cargo.toml @@ -11,7 +11,7 @@ bevy_prototype_inline_assets = "0.1.1" bevy_discovery = "0.1.0" #kurinji = "1.0.5" bevy_ldtk = {version = "0.4.2", features = ["bevy-unstable"]} -rayon = "1.5" +noise = "0.7.0" [dependencies.bevy] git = "https://github.com/bevyengine/bevy" diff --git a/src/entities/common.rs b/src/entities/common.rs @@ -1,3 +1,3 @@ pub struct Health { - pub hp: f32, + pub hp: f64, } diff --git a/src/entities/markers.rs b/src/entities/markers.rs @@ -1,4 +1,9 @@ /// Marker to help identify the player pub struct Player; /// Marker for hostiles +#[allow(dead_code)] pub struct Enemy; +/// Marker for walls +pub struct Wall; +/// Marker for movable places +pub struct Movable; diff --git a/src/entities/player.rs b/src/entities/player.rs @@ -3,7 +3,7 @@ use crate::entities::markers::Player; use bevy::prelude::*; #[derive(Debug)] -pub struct PlayerXp(pub u32); +pub struct PlayerXp(pub f64); pub struct PlayerName(pub String); diff --git a/src/main.rs b/src/main.rs @@ -1,11 +1,12 @@ +use crate::plugins::world::{SPRITE_HEIGHT, SPRITE_WIDTH}; use crate::plugins::{ + player::PLAYER_START, world::{MainCamera, WorldState}, PlayerPlugin, WorldPlugin, }; use bevy::diagnostic::{FrameTimeDiagnosticsPlugin, LogDiagnosticsPlugin}; use bevy::render::camera::{OrthographicProjection, ScalingMode}; use bevy::{prelude::*, window::WindowMode}; -use bevy_ldtk::*; mod entities; mod plugins; @@ -22,20 +23,19 @@ fn main() { title: "Random test game".to_string(), width: 1024., height: 720., - vsync: false, + vsync: true, resizable: true, mode: WindowMode::Windowed, ..Default::default() }) .init_resource::<GameState>() .add_plugins(DefaultPlugins) - .add_plugin(LdtkPlugin) .add_plugin(FrameTimeDiagnosticsPlugin::default()) .add_plugin(LogDiagnosticsPlugin::default()) - //.add_plugin(KurinjiPlugin::default()) - .add_startup_system(setup.system()) - .add_plugin(PlayerPlugin) + .add_startup_system_to_stage(StartupStage::PreStartup, setup.system()) .add_plugin(WorldPlugin) + .add_plugin(PlayerPlugin) + .add_system(bevy::input::system::exit_on_esc_system.system()) .run(); } @@ -49,15 +49,13 @@ fn setup(commands: &mut Commands /*mut kurinji: ResMut<Kurinji>*/) { scaling_mode: ScalingMode::FixedVertical, ..Default::default() }, + transform: Transform::from_translation(Vec3::new( + SPRITE_WIDTH * PLAYER_START.0 as f32, + SPRITE_HEIGHT * PLAYER_START.1 as f32, + 0.0, + )), ..OrthographicCameraBundle::new_2d() }) + .with(PLAYER_START) .with(MainCamera); - - /*// TODO move to file - kurinji - .bind_keyboard_pressed(KeyCode::A, "MOVE_LEFT") - .bind_keyboard_pressed(KeyCode::D, "MOVE_RIGHT") - .bind_keyboard_pressed(KeyCode::Space, "JUMP") - .bind_keyboard_pressed(KeyCode::LShift, "SHIFT_MODIFIER") - .bind_keyboard_pressed(KeyCode::RShift, "SHIFT_MODIFIER");*/ } diff --git a/src/plugins/mod.rs b/src/plugins/mod.rs @@ -1,4 +1,4 @@ -mod player; +pub(crate) mod player; pub(crate) mod world; pub use player::PlayerPlugin; diff --git a/src/plugins/player.rs b/src/plugins/player.rs @@ -1,218 +1,159 @@ use crate::entities::common::Health; -use crate::entities::markers::Player; +use crate::entities::markers::{Movable, Player, Wall}; use crate::entities::player::{PlayerBundle, PlayerName, PlayerXp}; -use crate::plugins::world::MainCamera; +use crate::plugins::world::{GridLocation, SPRITE_HEIGHT, SPRITE_WIDTH}; use crate::GameState; -use bevy::math::Vec3Swizzles; use bevy::prelude::*; -use bevy_ldtk::LdtkMap; -use rayon::prelude::*; -use std::convert::TryInto; +use std::collections::HashMap; + +pub const PLAYER_START: GridLocation = GridLocation(0, 0); pub struct PlayerPlugin; impl Plugin for PlayerPlugin { fn build(&self, app: &mut AppBuilder) { app.add_system(player_movement.system()) - .add_system(spawn_player.system()); + .add_system(setup_player.system()) + .add_startup_system(setup_player.system()); } } -fn spawn_player( - mut game_state: ResMut<GameState>, - commands: &mut Commands, - map_query: Query<&Handle<LdtkMap>>, - map_assets: Res<Assets<LdtkMap>>, - mut camera: Query<&mut Transform, With<MainCamera>>, - mut texture_atlases: ResMut<Assets<TextureAtlas>>, +fn setup_player( + mut commands: &mut Commands, + asset_server: Res<AssetServer>, + texture_atlases: ResMut<Assets<TextureAtlas>>, + game_state: ResMut<GameState>, ) { - if game_state.spawned { - return; + if !game_state.spawned { + setup_player_internal( + PLAYER_START, + &mut commands, + asset_server, + texture_atlases, + game_state, + ); } - // Loop through all of the maps - for map_handle in map_query.iter() { - // We have to `if let` here because asset server may not have finished loading - // the map yet. - if let Some(map) = map_assets.get(map_handle) { - let level_idx = game_state.world_state.level; - - // Get the level from the project - let level = &map.project.levels[level_idx]; - - // Find the entities layer - let entities_layer = level - .layer_instances - .as_ref() // get a reference to the layer instances - .unwrap() // Unwrap the option ( this could be None, if there are no layers ) - .iter() // Iterate over the layers - .find(|&x| x.__identifier == "Entities") // Filter on the one we want - .unwrap(); // Unwrap it ( would be None if it could not find a layer "Entities" ) - - // Get the specific entity you want - let player_start = entities_layer - .entity_instances - .iter() // Iterate over our entities in the layer - .find(|x| x.__identifier == "Player") // Find the one we want - .unwrap(); // Unwrap it - - // Get the number of layers in the map and add one to it: this is how high we need to - // spawn the player so that he is on top of all the maps - let player_z = level.layer_instances.as_ref().unwrap().len() as f32 + 1.0; - - // Do something with map data - let entities = &mut map.project.defs.entities.iter(); - let tilesets = &mut map.project.defs.tilesets.iter(); - - let player_position = Vec3::new( - // The player x position is the entity's x position from the map data - player_start.px[0] as f32, - // The player y position is the entity's y position from the map data, but - // multiplied by negative one because in the LDtk map +y means down and not up. - -(player_start.px[1]) as f32, - // Spawn the player with the z value we determined earlier - player_z, - ); - - // Move camera initially - // assuming there is exactly one main camera entity, so this is OK - let mut camera_transform = camera.iter_mut().next().unwrap(); - camera_transform.translation = player_position; - - // Find player assets - if let Some(player_entity) = entities.find(|x| x.identifier == "Player") { - if let Some(tileset_id) = player_entity.tileset_id { - if let Some(tileset) = tilesets.find(|x| x.uid == tileset_id) { - if let Some(tileset_texture) = map.tile_sets.get(&tileset.identifier) { - let tile_id = player_entity.tile_id; - let texture_atlas = TextureAtlas::from_grid( - (*tileset_texture).clone(), - Vec2::new( - tileset.tile_grid_size as f32, - tileset.tile_grid_size as f32, - ), - (tileset.px_wid / tileset.tile_grid_size) - .try_into() - .unwrap(), - (tileset.px_hei / tileset.tile_grid_size) - .try_into() - .unwrap(), - ); +} - let texture_atlas_handle = texture_atlases.add(texture_atlas); - commands - .spawn(SpriteSheetBundle { - sprite: TextureAtlasSprite { - index: tile_id.unwrap() as u32, - ..Default::default() - }, - texture_atlas: texture_atlas_handle, - transform: Transform::from_translation(player_position), - ..Default::default() - }) - .with(PlayerBundle { - xp: PlayerXp(0), - name: PlayerName("Player1".into()), - health: Health { hp: 100.0 }, - _p: Player, - }); - game_state.spawned = true; - } else { - println!("Error: Cannot find tileset as asset!"); - } - } else { - println!("Error: Cannot find tilset with wanted id!"); - } - } else { - println!("Error: Cannot find player tileset!"); - } - } else { - println!("Error: Cannot find player in map!"); - } - } - } +fn setup_player_internal( + grid_location: GridLocation, + commands: &mut Commands, + asset_server: Res<AssetServer>, + mut texture_atlases: ResMut<Assets<TextureAtlas>>, + mut game_state: ResMut<GameState>, +) { + let texture_handle = asset_server.load("tilesets/0x72_DungeonTilesetII_v1.3.png"); + let texture_atlas = TextureAtlas::from_grid(texture_handle, Vec2::new(16.0, 16.0), 32, 32); + let texture_atlas_handle = texture_atlases.add(texture_atlas); + + // Spawn player + commands + .spawn(SpriteSheetBundle { + sprite: TextureAtlasSprite { + index: 362, + ..Default::default() + }, + transform: Transform::from_translation(Vec3::new( + SPRITE_WIDTH * grid_location.0 as f32, + SPRITE_HEIGHT * grid_location.1 as f32, + 0.0, + )), + texture_atlas: texture_atlas_handle, + ..Default::default() + }) + .with(grid_location) + .with(Movable) + .with(PlayerBundle { + xp: PlayerXp(0.0), + name: PlayerName("Player 1".into()), + health: Health { hp: 100.0 }, + _p: Player, + }); + game_state.spawned = true; } +#[allow(clippy::type_complexity)] fn player_movement( - time: Res<Time>, - game_state: ResMut<GameState>, - input: Res<Input<KeyCode>>, - mut player: Query<(&PlayerBundle, &mut Transform)>, - mut camera: Query<&mut Transform, With<MainCamera>>, + keyboard_input: Res<Input<KeyCode>>, + mut wall_query: Query<(Entity, &Wall, &GridLocation)>, + mut set: QuerySet<( + Query<(Entity, &Movable, &mut GridLocation)>, + Query<(Entity, &PlayerBundle, &GridLocation)>, + )>, ) { - let shift = input.pressed(KeyCode::LShift) || input.pressed(KeyCode::RShift); - let _ctrl = input.pressed(KeyCode::LControl) || input.pressed(KeyCode::RControl); - // TODO make sure we queue inputs and do all of them - - let mut direction = Vec3::zero(); - - if shift { - if input.pressed(KeyCode::A) { - direction -= Vec3::new(1.0, 0.0, 0.0) * 5.; + let _shift = keyboard_input.pressed(KeyCode::LShift) || keyboard_input.pressed(KeyCode::RShift); + let _ctrl = + keyboard_input.pressed(KeyCode::LControl) || keyboard_input.pressed(KeyCode::RControl); + + let delta = { + let mut delta = GridLocation(0, 0); + if keyboard_input.just_pressed(KeyCode::A) { + delta = GridLocation(-1, 0); } - - if input.pressed(KeyCode::D) { - direction += Vec3::new(1.0, 0.0, 0.0) * 5.; + if keyboard_input.just_pressed(KeyCode::D) { + delta = GridLocation(1, 0); } - } else { - if input.pressed(KeyCode::A) { - direction -= Vec3::new(2.5, 0.0, 0.0); + if keyboard_input.just_pressed(KeyCode::S) { + delta = GridLocation(0, -1); } - - if input.pressed(KeyCode::D) { - direction += Vec3::new(2.5, 0.0, 0.0); + if keyboard_input.just_pressed(KeyCode::W) { + delta = GridLocation(0, 1); } - } - - if input.pressed(KeyCode::Space) { - direction += Vec3::new(0.0, 1.0, 0.0); - } + if delta == GridLocation(0, 0) { + return; + } + delta + }; + + let immovables: HashMap<GridLocation, Entity> = { + let mut tmp = HashMap::new(); + for (wall_entity, _wall, wall_grid_location) in wall_query.iter_mut() { + tmp.insert( + GridLocation(wall_grid_location.0, wall_grid_location.1), + wall_entity, + ); + } + tmp + }; + + let movables: HashMap<GridLocation, Entity> = { + let mut tmp = HashMap::new(); + for (movable_entity, _movable, grid_location) in set.q0_mut().iter_mut() { + tmp.insert( + GridLocation(grid_location.0, grid_location.1), + movable_entity, + ); + } + tmp + }; - if input.pressed(KeyCode::S) { - direction -= Vec3::new(0.0, 1.0, 0.0); - } + let mut to_move: Vec<Entity> = vec![]; + let mut last_pos = None; - if direction != Vec3::zero() { - let translation = time.delta_seconds() * direction * 40.; + for (_player_entity, _player, player_grid_location) in set.q1().iter() { + let mut tmp_to_move = vec![]; - // assuming there is exactly one player entity, so this is OK - if let Some((_, mut player_transform)) = player.iter_mut().next() { - if let Some(mut camera_transform) = camera.iter_mut().next() { - let new_coords = player_transform.translation + translation; - let rounded_x = new_coords.x.round(); - let rounded_y = new_coords.y.round(); - let rounded_cords = Vec3::new(rounded_x, rounded_y, new_coords.z); - if can_move_to_requested_coordinate(&game_state, rounded_cords, 16, 16) { - player_transform.translation += translation; - camera_transform.translation += translation; - } + let mut current_loc = *player_grid_location; + //prevent block skips + if let Some(pos) = last_pos { + if pos == current_loc { + continue; } } - } -} -fn can_move_to_requested_coordinate( - game_state: &ResMut<GameState>, - coordinate: Vec3, - width: i32, - height: i32, -) -> bool { - // Do a bounding box check. Bounding boxes are 16*16 from center of the object - return !game_state - .world_state - .collisions - .clone() - .par_iter() - .any(|object_coordinate| { - check_intersection( - coordinate.xy(), - object_coordinate, - Vec2::new(width as f32, height as f32), - Vec2::new(16.0, 16.0), - ) - }); -} + while let Some(movable) = movables.get(&current_loc) { + tmp_to_move.push(*movable); + current_loc = current_loc + delta; + } + if let Some(_immovable) = immovables.get(&current_loc) { + continue; + } + last_pos = Some(current_loc); + to_move.append(&mut tmp_to_move); + } -fn check_intersection(a: Vec2, b: &Vec2, a_size: Vec2, b_size: Vec2) -> bool { - ((a.x - b.x).abs() * 2.0 < (a_size.x + b_size.x)) - && ((a.y - b.y).abs() * 2.0 < (a_size.y + b_size.y)) + for loc in to_move { + let mut grid_location: Mut<GridLocation> = set.q0_mut().get_component_mut(loc).unwrap(); + *grid_location = *grid_location + delta; + } } diff --git a/src/plugins/world.rs b/src/plugins/world.rs @@ -1,7 +1,8 @@ +use crate::entities::markers::Wall; use crate::GameState; use bevy::prelude::*; -use bevy_ldtk::{LdtkMap, LdtkMapBundle, LdtkMapConfig}; -use rayon::prelude::*; +use noise::{Abs, NoiseFn, OpenSimplex}; +use std::ops; pub struct MainCamera; @@ -13,79 +14,98 @@ pub struct WorldState { pub requested_level: usize, pub world: Option<Entity>, pub collisions: Vec<Vec2>, + pub world_noise: OpenSimplex, } pub struct WorldPlugin; -impl Plugin for WorldPlugin { - fn build(&self, app: &mut AppBuilder) { - app.add_system(draw.system()) - .add_system(setup_collisions.system()); +#[derive(Hash, Eq, PartialEq, Debug, Clone, Copy)] +pub struct GridLocation(pub i32, pub i32); + +impl ops::Add<GridLocation> for GridLocation { + type Output = GridLocation; + + fn add(self, rhs: GridLocation) -> Self::Output { + GridLocation(self.0 + rhs.0, self.1 + rhs.1) } } -pub fn setup_collisions( - map_query: Query<&Handle<LdtkMap>>, - map_assets: Res<Assets<LdtkMap>>, - mut game_state: ResMut<GameState>, -) { - if game_state.world_state.collisions_loaded - && game_state.world_state.level == game_state.world_state.requested_level - { - return; +impl From<Vec2> for GridLocation { + fn from(vec: Vec2) -> Self { + Self { + 0: vec.x.round() as i32, + 1: vec.y.round() as i32, + } } +} - // Loop through all of the maps - for map_handle in map_query.iter() { - // We have to `if let` here because asset server may not have finished loading - // the map yet. - if let Some(map) = map_assets.get(map_handle) { - let level_idx = game_state.world_state.level; - - // Get the level from the project - let level = &map.project.levels[level_idx]; - - // Find the collision layer - let collision_layer = level - .layer_instances - .as_ref() // get a reference to the layer instances - .unwrap() // Unwrap the option ( this could be None, if there are no layers ) - .iter() // Iterate over the layers - .find(|&x| x.__identifier == "Collisions") // Filter on the one we want - .unwrap(); // Unwrap it ( would be None if it could not find a layer "Collisions" ) - - // Calculate collider center coordinates - game_state.world_state.collisions = collision_layer - .int_grid_csv - .clone() - .into_par_iter() - .enumerate() - .filter(|(_, object)| *object != 2 && *object != 0) - .map(|(i, _)| { - one_d_to_two_d_coordinate(i as f32, collision_layer.__c_wid as f32, 16.0, 16.0) - }) - .collect(); - game_state.world_state.collisions_loaded = true; +impl From<[f64; 2]> for GridLocation { + fn from(coords: [f64; 2]) -> Self { + Self { + 0: coords[0] as i32, + 1: coords[1] as i32, } } } -fn one_d_to_two_d_coordinate( - coordinate: f32, - row_length: f32, - tile_width: f32, - tile_height: f32, -) -> Vec2 { - Vec2::new( - ((coordinate % row_length).round() * tile_width + 11.0).round() as f32, - (-((coordinate / row_length).round() * tile_height + 8.0)).round() as f32, - ) +impl From<GridLocation> for [f64; 2] { + fn from(loc: GridLocation) -> Self { + [loc.0 as f64, loc.1 as f64] + } +} + +const LERP_LAMBDA: f32 = 5.0; + +fn render_grid_location_to_transform( + time: Res<Time>, + mut query: Query<(&GridLocation, &mut Transform)>, +) { + for (grid_location, mut transform) in query.iter_mut() { + let target_x = SPRITE_WIDTH * grid_location.0 as f32; + transform.translation.x = transform.translation.x + * (1.0 - LERP_LAMBDA * time.delta_seconds()) + + target_x * LERP_LAMBDA * time.delta_seconds(); + let target_y = SPRITE_WIDTH * grid_location.1 as f32; + transform.translation.y = transform.translation.y + * (1.0 - LERP_LAMBDA * time.delta_seconds()) + + target_y * LERP_LAMBDA * time.delta_seconds(); + } +} + +impl Plugin for WorldPlugin { + fn build(&self, app: &mut AppBuilder) { + app.add_system(draw.system()) + .add_system(render_grid_location_to_transform.system()); + } +} + +pub const SPRITE_WIDTH: f32 = 16.0; +pub const SPRITE_HEIGHT: f32 = 16.0; + +fn setup_wall( + grid_location: GridLocation, + commands: &mut Commands, + materials: &mut ResMut<Assets<ColorMaterial>>, +) { + commands + .spawn(SpriteBundle { + material: materials.add(Color::rgb(0.1, 0.1, 0.1).into()), + transform: Transform::from_translation(Vec3::new( + SPRITE_WIDTH * grid_location.0 as f32, + SPRITE_HEIGHT * grid_location.1 as f32, + -1.0, + )), + sprite: Sprite::new(Vec2::new(SPRITE_WIDTH, SPRITE_HEIGHT)), + ..Default::default() + }) + .with(grid_location) + .with(Wall); } fn draw( commands: &mut Commands, - asset_server: Res<AssetServer>, mut game_state: ResMut<GameState>, + mut materials: ResMut<Assets<ColorMaterial>>, ) { if game_state.world_state.map_loaded && game_state.world_state.level == game_state.world_state.requested_level @@ -93,29 +113,31 @@ fn draw( return; } - if let Some(world) = game_state.world_state.world { - commands.remove::<LdtkMapBundle>(world); - } + game_state.world_state.world_noise = OpenSimplex::new(); + let noise = Abs::new(&game_state.world_state.world_noise); - commands // Spawn a map bundle - .spawn(LdtkMapBundle { - // Specify the path to the map asset to load - map: asset_server.load("map.ldtk"), - config: LdtkMapConfig { - // Automatically set the clear color to the LDtk background color - set_clear_color: true, - // You can specify a scale or leave it set to 1 for 1 to 1 pixel size - scale: 1.0, - // Set which level to load out of the map or leave it to 0 for the default level - level: game_state.world_state.requested_level, - // Tell the map to center around it's `Transform` instead of putting the top-left - // corner of the map at the origin `Transform`. - center_map: false, - }, - ..Default::default() - }); + for chunk_y in -2..2 { + for chunk_x in -2..2 { + for y in -16..16 { + for x in -16..16 { + let full_x = (chunk_x * 32) + x; + let full_y = (chunk_y * 32) + y; + let coord = GridLocation(full_x, full_y); + if full_x == 0 && full_y == 0 { + continue; + } + let noise_value = noise.get(Into::<[f64; 2]>::into(coord)); + //println!("X: {}, Y: {}, Noise: {}", x, y, noise_value); - game_state.world_state.world = commands.current_entity(); + // scale and center at screen-center + // TODO see https://stackoverflow.com/a/10225718 + if noise_value < 0.2 { + setup_wall(coord, commands, &mut materials); + } + } + } + } + } game_state.world_state.level = game_state.world_state.requested_level; game_state.world_state.map_loaded = true;