From d3a09df7a898af75b34c587aba15c8ab8aa33961 Mon Sep 17 00:00:00 2001 From: Llywelwyn Date: Thu, 6 Jul 2023 16:47:07 +0100 Subject: [PATCH] initial commit using rltk --- Cargo.lock | 2287 +++++++++++++++++++++++++++++ Cargo.toml | 11 + resources/backing.fs | 12 + resources/backing.vs | 11 + resources/console_no_bg.fs | 17 + resources/console_no_bg.vs | 17 + resources/console_with_bg.fs | 16 + resources/console_with_bg.vs | 17 + resources/example_tiles.jpg | Bin 0 -> 1928 bytes resources/example_tiles.xcf | Bin 0 -> 2957 bytes resources/mltest.xp | Bin 0 -> 62 bytes resources/nyan.xp | Bin 0 -> 393 bytes resources/scanlines.fs | 26 + resources/scanlines.vs | 11 + resources/terminal10x10_gs_tc.png | Bin 0 -> 8804 bytes resources/terminal8x8.jpg | Bin 0 -> 44266 bytes resources/vga8x16.jpg | Bin 0 -> 38874 bytes src/components.rs | 66 + src/damage_system.rs | 50 + src/gamelog.rs | 3 + src/gui.rs | 112 ++ src/main.rs | 176 +++ src/map.rs | 224 +++ src/map_indexing_system.rs | 26 + src/melee_combat_system.rs | 41 + src/monster_ai_system.rs | 62 + src/player.rs | 76 + src/rect.rs | 21 + src/visibility_system.rs | 41 + 29 files changed, 3323 insertions(+) create mode 100644 Cargo.lock create mode 100644 Cargo.toml create mode 100644 resources/backing.fs create mode 100644 resources/backing.vs create mode 100644 resources/console_no_bg.fs create mode 100644 resources/console_no_bg.vs create mode 100644 resources/console_with_bg.fs create mode 100644 resources/console_with_bg.vs create mode 100644 resources/example_tiles.jpg create mode 100644 resources/example_tiles.xcf create mode 100644 resources/mltest.xp create mode 100644 resources/nyan.xp create mode 100644 resources/scanlines.fs create mode 100644 resources/scanlines.vs create mode 100644 resources/terminal10x10_gs_tc.png create mode 100644 resources/terminal8x8.jpg create mode 100644 resources/vga8x16.jpg create mode 100644 src/components.rs create mode 100644 src/damage_system.rs create mode 100644 src/gamelog.rs create mode 100644 src/gui.rs create mode 100644 src/main.rs create mode 100644 src/map.rs create mode 100644 src/map_indexing_system.rs create mode 100644 src/melee_combat_system.rs create mode 100644 src/monster_ai_system.rs create mode 100644 src/player.rs create mode 100644 src/rect.rs create mode 100644 src/visibility_system.rs diff --git a/Cargo.lock b/Cargo.lock new file mode 100644 index 0000000..7cb14ad --- /dev/null +++ b/Cargo.lock @@ -0,0 +1,2287 @@ +# This file is automatically @generated by Cargo. +# It is not intended for manual editing. +version = 3 + +[[package]] +name = "adler" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" + +[[package]] +name = "ahash" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e8fd72866655d1904d6b0997d0b07ba561047d070fbe29de039031c641b61217" + +[[package]] +name = "aho-corasick" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43f6cb1bf222025340178f382c426f13757b2960e89779dfcb319c32542a5a41" +dependencies = [ + "memchr", +] + +[[package]] +name = "anyhow" +version = "1.0.71" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c7d0618f0e0b7e8ff11427422b64564d5fb0be1940354bfe2e0529b18a9d9b8" + +[[package]] +name = "arrayref" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6b4930d2cb77ce62f89ee5d5289b4ac049559b1c45539271f5ed4fdc7db34545" + +[[package]] +name = "arrayvec" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" + +[[package]] +name = "atom" +version = "0.3.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c9ff149ed9780025acfdb36862d35b28856bb693ceb451259a7164442f22fdc3" + +[[package]] +name = "autocfg" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" + +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "block" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0d8c1fef690941d3e7788d328517591fecc684c084084702d6ff1641e993699a" + +[[package]] +name = "bracket-algorithm-traits" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4a13fb98ac33e6cd03fc035d8503f8a80b38c523737c9f84b400a4b9e065cfd3" +dependencies = [ + "bracket-geometry", + "smallvec", +] + +[[package]] +name = "bracket-color" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7333827cf727ceb302cc4f638cc8befc87f5f1423873255d94cc0a24009e940a" +dependencies = [ + "lazy_static", + "parking_lot 0.12.1", +] + +[[package]] +name = "bracket-embedding" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1cb6747f25903066109a619e3d580ef5ff7b3ffc281fa51ece473e1396e2298" +dependencies = [ + "lazy_static", + "parking_lot 0.12.1", +] + +[[package]] +name = "bracket-geometry" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0f31b525fcd65027885f3a1e3a250a5dd397d70de4a6a5a125f03e0bef951499" +dependencies = [ + "ultraviolet", +] + +[[package]] +name = "bracket-lib" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43bbe13e39628e7f73673737c825001494dee7329cee8ee79dfeaa7cfd136dbf" +dependencies = [ + "bracket-algorithm-traits", + "bracket-color", + "bracket-geometry", + "bracket-noise", + "bracket-pathfinding", + "bracket-random", + "bracket-terminal", +] + +[[package]] +name = "bracket-noise" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f0b7443d0990c69db7a83f376f0101d684c20a911698e5f932bffbda2c8b08dd" +dependencies = [ + "bracket-random", +] + +[[package]] +name = "bracket-pathfinding" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32ae7f2ebf242316ba10e84ca3b31af064b8c0c77402b2171a3104a2a77718fc" +dependencies = [ + "bracket-algorithm-traits", + "bracket-geometry", + "num-rational", + "smallvec", +] + +[[package]] +name = "bracket-random" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "437be61484077b1ddb57002ce3c96b7d03cbf500b5d15157ee7e67e22332c39b" +dependencies = [ + "getrandom", + "js-sys", + "lazy_static", + "rand", + "rand_xorshift", + "regex", + "wasm-bindgen", +] + +[[package]] +name = "bracket-rex" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c4735d15070b98d0f07360d62914d1524679325019cae46c7af73637a6ef196a" +dependencies = [ + "bracket-color", + "bracket-embedding", + "byteorder", + "flate2", +] + +[[package]] +name = "bracket-terminal" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2493063cb676e2e9e3a3a630eee032a297e43c8a1cee08c94feaad3344ed0b46" +dependencies = [ + "anyhow", + "bracket-color", + "bracket-embedding", + "bracket-geometry", + "bracket-rex", + "console_error_panic_hook", + "glow", + "glutin", + "image", + "lazy_static", + "object-pool", + "parking_lot 0.12.1", + "rand", + "ultraviolet", + "wasm-bindgen", + "wasm-timer", + "web-sys", + "winit 0.26.1", + "winit 0.27.5", +] + +[[package]] +name = "bumpalo" +version = "3.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1" + +[[package]] +name = "bytemuck" +version = "1.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "17febce684fd15d89027105661fec94afb475cb995fbc59d2865198446ba2eea" + +[[package]] +name = "byteorder" +version = "1.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "14c189c53d098945499cdfa7ecc63567cf3886b3332b312a5b4585d8d3a6a610" + +[[package]] +name = "calloop" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bf2eec61efe56aa1e813f5126959296933cf0700030e4314786c48779a66ab82" +dependencies = [ + "log", + "nix 0.22.3", +] + +[[package]] +name = "calloop" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "52e0d00eb1ea24371a97d2da6201c6747a633dc6dc1988ef503403b4c59504a8" +dependencies = [ + "bitflags", + "log", + "nix 0.25.1", + "slotmap", + "thiserror", + "vec_map", +] + +[[package]] +name = "cc" +version = "1.0.79" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "50d30906286121d95be3d479533b458f87493b30a4b5f79a607db8f5d11aa91f" + +[[package]] +name = "cfg-if" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" + +[[package]] +name = "cfg-if" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" + +[[package]] +name = "cgl" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ced0551234e87afee12411d535648dd89d2e7f34c78b753395567aff3d447ff" +dependencies = [ + "libc", +] + +[[package]] +name = "cmake" +version = "0.1.50" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a31c789563b815f77f4250caee12365734369f942439b7defd71e18a48197130" +dependencies = [ + "cc", +] + +[[package]] +name = "cocoa" +version = "0.24.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f425db7937052c684daec3bd6375c8abe2d146dca4b8b143d6db777c39138f3a" +dependencies = [ + "bitflags", + "block", + "cocoa-foundation", + "core-foundation 0.9.3", + "core-graphics 0.22.3", + "foreign-types 0.3.2", + "libc", + "objc", +] + +[[package]] +name = "cocoa-foundation" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "931d3837c286f56e3c58423ce4eba12d08db2374461a785c86f672b08b5650d6" +dependencies = [ + "bitflags", + "block", + "core-foundation 0.9.3", + "core-graphics-types", + "foreign-types 0.3.2", + "libc", + "objc", +] + +[[package]] +name = "color_quant" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d7b894f5411737b7867f4827955924d7c254fc9f4d91a6aad6b097804b1018b" + +[[package]] +name = "console_error_panic_hook" +version = "0.1.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a06aeb73f470f66dcdbf7223caeebb85984942f22f1adb2a088cf9668146bbbc" +dependencies = [ + "cfg-if 1.0.0", + "wasm-bindgen", +] + +[[package]] +name = "core-foundation" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57d24c7a13c43e870e37c1556b74555437870a04514f7685f5b354e090567171" +dependencies = [ + "core-foundation-sys 0.7.0", + "libc", +] + +[[package]] +name = "core-foundation" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" +dependencies = [ + "core-foundation-sys 0.8.4", + "libc", +] + +[[package]] +name = "core-foundation-sys" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3a71ab494c0b5b860bdc8407ae08978052417070c2ced38573a9157ad75b8ac" + +[[package]] +name = "core-foundation-sys" +version = "0.8.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" + +[[package]] +name = "core-graphics" +version = "0.19.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b3889374e6ea6ab25dba90bb5d96202f61108058361f6dc72e8b03e6f8bbe923" +dependencies = [ + "bitflags", + "core-foundation 0.7.0", + "foreign-types 0.3.2", + "libc", +] + +[[package]] +name = "core-graphics" +version = "0.22.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2581bbab3b8ffc6fcbd550bf46c355135d16e9ff2a6ea032ad6b9bf1d7efe4fb" +dependencies = [ + "bitflags", + "core-foundation 0.9.3", + "core-graphics-types", + "foreign-types 0.3.2", + "libc", +] + +[[package]] +name = "core-graphics-types" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2bb142d41022986c1d8ff29103a1411c8a3dfad3552f87a4f8dc50d61d4f4e33" +dependencies = [ + "bitflags", + "core-foundation 0.9.3", + "libc", +] + +[[package]] +name = "core-text" +version = "19.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "99d74ada66e07c1cefa18f8abfba765b486f250de2e4a999e5727fc0dd4b4a25" +dependencies = [ + "core-foundation 0.9.3", + "core-graphics 0.22.3", + "foreign-types 0.3.2", + "libc", +] + +[[package]] +name = "core-video-sys" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34ecad23610ad9757664d644e369246edde1803fcb43ed72876565098a5d3828" +dependencies = [ + "cfg-if 0.1.10", + "core-foundation-sys 0.7.0", + "core-graphics 0.19.2", + "libc", + "objc", +] + +[[package]] +name = "crc32fast" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b540bd8bc810d3885c6ea91e2018302f68baba2129ab3e88f32389ee9370880d" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "crossbeam-channel" +version = "0.5.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a33c2bf77f2df06183c3aa30d1e96c0695a313d4f9c453cc3762a6db39f99200" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-deque" +version = "0.8.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ce6fd6f855243022dcecf8702fef0c297d4338e226845fe067f6341ad9fa0cef" +dependencies = [ + "cfg-if 1.0.0", + "crossbeam-epoch", + "crossbeam-utils 0.8.16", +] + +[[package]] +name = "crossbeam-epoch" +version = "0.9.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ae211234986c545741a7dc064309f67ee1e5ad243d0e48335adc0484d960bcc7" +dependencies = [ + "autocfg", + "cfg-if 1.0.0", + "crossbeam-utils 0.8.16", + "memoffset 0.9.0", + "scopeguard", +] + +[[package]] +name = "crossbeam-queue" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "774ba60a54c213d409d5353bda12d49cd68d14e45036a285234c8d6f91f92570" +dependencies = [ + "cfg-if 0.1.10", + "crossbeam-utils 0.7.2", + "maybe-uninit", +] + +[[package]] +name = "crossbeam-utils" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c3c7c73a2d1e9fc0886a08b93e98eb643461230d5f1925e4036204d5f2e261a8" +dependencies = [ + "autocfg", + "cfg-if 0.1.10", + "lazy_static", +] + +[[package]] +name = "crossbeam-utils" +version = "0.8.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a22b2d63d4d1dc0b7f1b6b2747dd0088008a9be28b6ddf0b1e7d335e3037294" +dependencies = [ + "cfg-if 1.0.0", +] + +[[package]] +name = "crossfont" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "21fd3add36ea31aba1520aa5288714dd63be506106753226d0eb387a93bc9c45" +dependencies = [ + "cocoa", + "core-foundation 0.9.3", + "core-foundation-sys 0.8.4", + "core-graphics 0.22.3", + "core-text", + "dwrote", + "foreign-types 0.5.0", + "freetype-rs", + "libc", + "log", + "objc", + "once_cell", + "pkg-config", + "servo-fontconfig", + "winapi", +] + +[[package]] +name = "cty" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b365fabc795046672053e29c954733ec3b05e4be654ab130fe8f1f94d7051f35" + +[[package]] +name = "darling" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a01d95850c592940db9b8194bc39f4bc0e89dee5c4265e4b1807c34a9aba453c" +dependencies = [ + "darling_core", + "darling_macro", +] + +[[package]] +name = "darling_core" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "859d65a907b6852c9361e3185c862aae7fafd2887876799fa55f5f99dc40d610" +dependencies = [ + "fnv", + "ident_case", + "proc-macro2", + "quote", + "strsim", + "syn 1.0.109", +] + +[[package]] +name = "darling_macro" +version = "0.13.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c972679f83bdf9c42bd905396b6c3588a843a17f0f16dfcfa3e2c5d57441835" +dependencies = [ + "darling_core", + "quote", + "syn 1.0.109", +] + +[[package]] +name = "dispatch" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bd0c93bb4b0c6d9b77f4435b0ae98c24d17f1c45b2ff844c6151a07256ca923b" + +[[package]] +name = "dlib" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "330c60081dcc4c72131f8eb70510f1ac07223e5d4163db481a04a0befcffa412" +dependencies = [ + "libloading 0.8.0", +] + +[[package]] +name = "downcast-rs" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9ea835d29036a4087793836fa931b08837ad5e957da9e23886b29586fb9b6650" + +[[package]] +name = "dwrote" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "439a1c2ba5611ad3ed731280541d36d2e9c4ac5e7fb818a27b604bdc5a6aa65b" +dependencies = [ + "lazy_static", + "libc", + "serde", + "serde_derive", + "winapi", + "wio", +] + +[[package]] +name = "either" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7fcaabb2fef8c910e7f4c7ce9f67a1283a1715879a7c230ca9d6d1ae31f16d91" + +[[package]] +name = "equivalent" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "88bffebc5d80432c9b140ee17875ff173a8ab62faad5b257da912bd2f6c1c0a1" + +[[package]] +name = "expat-sys" +version = "2.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "658f19728920138342f68408b7cf7644d90d4784353d8ebc32e7e8663dbe45fa" +dependencies = [ + "cmake", + "pkg-config", +] + +[[package]] +name = "fdeflate" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d329bdeac514ee06249dabc27877490f17f5d371ec693360768b838e19f3ae10" +dependencies = [ + "simd-adler32", +] + +[[package]] +name = "flate2" +version = "1.0.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b9429470923de8e8cbd4d2dc513535400b4b3fef0319fb5c4e1f520a7bef743" +dependencies = [ + "crc32fast", + "miniz_oxide", +] + +[[package]] +name = "fnv" +version = "1.0.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" + +[[package]] +name = "foreign-types" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f6f339eb8adc052cd2ca78910fda869aefa38d22d5cb648e6485e4d3fc06f3b1" +dependencies = [ + "foreign-types-shared 0.1.1", +] + +[[package]] +name = "foreign-types" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d737d9aa519fb7b749cbc3b962edcf310a8dd1f4b67c91c4f83975dbdd17d965" +dependencies = [ + "foreign-types-macros", + "foreign-types-shared 0.3.1", +] + +[[package]] +name = "foreign-types-macros" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a5c6c585bc94aaf2c7b51dd4c2ba22680844aba4c687be581871a6f518c5742" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.23", +] + +[[package]] +name = "foreign-types-shared" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" + +[[package]] +name = "foreign-types-shared" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "aa9a19cbb55df58761df49b23516a86d432839add4af60fc256da840f66ed35b" + +[[package]] +name = "freetype-rs" +version = "0.26.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74eadec9d0a5c28c54bb9882e54787275152a4e36ce206b45d7451384e5bf5fb" +dependencies = [ + "bitflags", + "freetype-sys", + "libc", +] + +[[package]] +name = "freetype-sys" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a37d4011c0cc628dfa766fcc195454f4b068d7afdc2adfd28861191d866e731a" +dependencies = [ + "cmake", + "libc", + "pkg-config", +] + +[[package]] +name = "futures" +version = "0.1.31" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3a471a38ef8ed83cd6e40aa59c1ffe17db6855c18e3604d9c4ed8c08ebc28678" + +[[package]] +name = "getrandom" +version = "0.2.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be4136b2a15dd319360be1c07d9933517ccf0be8f16bf62a3bee4f0d618df427" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "wasi", +] + +[[package]] +name = "gl_generator" +version = "0.14.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a95dfc23a2b4a9a2f5ab41d194f8bfda3cabec42af4e39f08c339eb2a0c124d" +dependencies = [ + "khronos_api", + "log", + "xml-rs", +] + +[[package]] +name = "glow" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d8bd5877156a19b8ac83a29b2306fe20537429d318f3ff0a1a2119f8d9c61919" +dependencies = [ + "js-sys", + "slotmap", + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "glutin" +version = "0.29.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "444c9ad294fdcaf20ccf6726b78f380b5450275540c9b68ab62f49726ad1c713" +dependencies = [ + "cgl", + "cocoa", + "core-foundation 0.9.3", + "glutin_egl_sys", + "glutin_gles2_sys", + "glutin_glx_sys", + "glutin_wgl_sys", + "libloading 0.7.4", + "log", + "objc", + "once_cell", + "osmesa-sys", + "parking_lot 0.12.1", + "raw-window-handle 0.5.2", + "wayland-client", + "wayland-egl", + "winapi", + "winit 0.27.5", +] + +[[package]] +name = "glutin_egl_sys" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68900f84b471f31ea1d1355567eb865a2cf446294f06cef8d653ed7bcf5f013d" +dependencies = [ + "gl_generator", + "winapi", +] + +[[package]] +name = "glutin_gles2_sys" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e8094e708b730a7c8a1954f4f8a31880af00eb8a1c5b5bf85d28a0a3c6d69103" +dependencies = [ + "gl_generator", + "objc", +] + +[[package]] +name = "glutin_glx_sys" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d93d0575865098580c5b3a423188cd959419912ea60b1e48e8b3b526f6d02468" +dependencies = [ + "gl_generator", + "x11-dl", +] + +[[package]] +name = "glutin_wgl_sys" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3da5951a1569dbab865c6f2a863efafff193a93caf05538d193e9e3816d21696" +dependencies = [ + "gl_generator", +] + +[[package]] +name = "hashbrown" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96282e96bfcd3da0d3aa9938bedf1e50df3269b6db08b4876d2da0bb1a0841cf" +dependencies = [ + "ahash", + "autocfg", +] + +[[package]] +name = "hashbrown" +version = "0.14.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2c6201b9ff9fd90a5a3bac2e56a830d0caa509576f0e503818ee82c181b3437a" + +[[package]] +name = "hermit-abi" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "443144c8cdadd93ebf52ddb4056d257f5b52c04d3c804e657d19eb73fc33668b" + +[[package]] +name = "hibitset" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93a1bb8316a44459a7d14253c4d28dd7395cbd23cc04a68c46e851b8e46d64b1" +dependencies = [ + "atom", + "rayon", +] + +[[package]] +name = "ident_case" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39" + +[[package]] +name = "image" +version = "0.24.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "527909aa81e20ac3a44803521443a765550f09b5130c2c2fa1ea59c2f8f50a3a" +dependencies = [ + "bytemuck", + "byteorder", + "color_quant", + "jpeg-decoder", + "num-rational", + "num-traits", + "png", +] + +[[package]] +name = "indexmap" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5477fe2230a79769d8dc68e0eabf5437907c0457a5614a9e8dddb67f65eb65d" +dependencies = [ + "equivalent", + "hashbrown 0.14.0", +] + +[[package]] +name = "instant" +version = "0.1.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" +dependencies = [ + "cfg-if 1.0.0", + "js-sys", + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "jni-sys" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8eaf4bc02d17cbdd7ff4c7438cafcdf7fb9a4613313ad11b4f8fefe7d3fa0130" + +[[package]] +name = "jpeg-decoder" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bc0000e42512c92e31c2252315bda326620a4e034105e900c98ec492fa077b3e" + +[[package]] +name = "js-sys" +version = "0.3.64" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c5f195fe497f702db0f318b07fdd68edb16955aed830df8363d837542f8f935a" +dependencies = [ + "wasm-bindgen", +] + +[[package]] +name = "khronos_api" +version = "3.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2db585e1d738fc771bf08a151420d3ed193d9d895a36df7f6f8a9456b911ddc" + +[[package]] +name = "lazy_static" +version = "1.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" + +[[package]] +name = "libc" +version = "0.2.147" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4668fb0ea861c1df094127ac5f1da3409a82116a4ba74fca2e58ef927159bb3" + +[[package]] +name = "libloading" +version = "0.7.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b67380fd3b2fbe7527a606e18729d21c6f3951633d0500574c4dc22d2d638b9f" +dependencies = [ + "cfg-if 1.0.0", + "winapi", +] + +[[package]] +name = "libloading" +version = "0.8.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d580318f95776505201b28cf98eb1fa5e4be3b689633ba6a3e6cd880ff22d8cb" +dependencies = [ + "cfg-if 1.0.0", + "windows-sys 0.48.0", +] + +[[package]] +name = "lock_api" +version = "0.4.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1cc9717a20b1bb222f333e6a92fd32f7d8a18ddc5a3191a11af45dcbf4dcd16" +dependencies = [ + "autocfg", + "scopeguard", +] + +[[package]] +name = "log" +version = "0.4.19" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b06a4cde4c0f271a446782e3eff8de789548ce57dbc8eca9292c27f4a42004b4" + +[[package]] +name = "malloc_buf" +version = "0.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62bb907fe88d54d8d9ce32a3cceab4218ed2f6b7d35617cafe9adf84e43919cb" +dependencies = [ + "libc", +] + +[[package]] +name = "maybe-uninit" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60302e4db3a61da70c0cb7991976248362f30319e88850c487b9b95bbf059e00" + +[[package]] +name = "memchr" +version = "2.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" + +[[package]] +name = "memmap2" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "00b6c2ebff6180198788f5db08d7ce3bc1d0b617176678831a7510825973e357" +dependencies = [ + "libc", +] + +[[package]] +name = "memmap2" +version = "0.5.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "83faa42c0a078c393f6b29d5db232d8be22776a891f8f56e5284faee4a20b327" +dependencies = [ + "libc", +] + +[[package]] +name = "memoffset" +version = "0.6.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce" +dependencies = [ + "autocfg", +] + +[[package]] +name = "memoffset" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a634b1c61a95585bd15607c6ab0c4e5b226e695ff2800ba0cdccddf208c406c" +dependencies = [ + "autocfg", +] + +[[package]] +name = "minimal-lexical" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" + +[[package]] +name = "miniz_oxide" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7" +dependencies = [ + "adler", + "simd-adler32", +] + +[[package]] +name = "mio" +version = "0.8.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "927a765cd3fc26206e66b296465fa9d3e5ab003e651c1b3c060e7956d96b19d2" +dependencies = [ + "libc", + "log", + "wasi", + "windows-sys 0.48.0", +] + +[[package]] +name = "mopa" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a785740271256c230f57462d3b83e52f998433a7062fc18f96d5999474a9f915" + +[[package]] +name = "ndk" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96d868f654c72e75f8687572699cdabe755f03effbb62542768e995d5b8d699d" +dependencies = [ + "bitflags", + "jni-sys", + "ndk-sys 0.2.2", + "num_enum", + "thiserror", +] + +[[package]] +name = "ndk" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "451422b7e4718271c8b5b3aadf5adedba43dc76312454b387e98fae0fc951aa0" +dependencies = [ + "bitflags", + "jni-sys", + "ndk-sys 0.4.1+23.1.7779620", + "num_enum", + "raw-window-handle 0.5.2", + "thiserror", +] + +[[package]] +name = "ndk-context" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "27b02d87554356db9e9a873add8782d4ea6e3e58ea071a9adb9a2e8ddb884a8b" + +[[package]] +name = "ndk-glue" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c71bee8ea72d685477e28bd004cfe1bf99c754d688cd78cad139eae4089484d4" +dependencies = [ + "lazy_static", + "libc", + "log", + "ndk 0.5.0", + "ndk-context", + "ndk-macro", + "ndk-sys 0.2.2", +] + +[[package]] +name = "ndk-glue" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0434fabdd2c15e0aab768ca31d5b7b333717f03cf02037d5a0a3ff3c278ed67f" +dependencies = [ + "libc", + "log", + "ndk 0.7.0", + "ndk-context", + "ndk-macro", + "ndk-sys 0.4.1+23.1.7779620", + "once_cell", + "parking_lot 0.12.1", +] + +[[package]] +name = "ndk-macro" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0df7ac00c4672f9d5aece54ee3347520b7e20f158656c7db2e6de01902eb7a6c" +dependencies = [ + "darling", + "proc-macro-crate", + "proc-macro2", + "quote", + "syn 1.0.109", +] + +[[package]] +name = "ndk-sys" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1bcdd74c20ad5d95aacd60ef9ba40fdf77f767051040541df557b7a9b2a2121" + +[[package]] +name = "ndk-sys" +version = "0.4.1+23.1.7779620" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3cf2aae958bd232cac5069850591667ad422d263686d75b52a065f9badeee5a3" +dependencies = [ + "jni-sys", +] + +[[package]] +name = "nix" +version = "0.22.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e4916f159ed8e5de0082076562152a76b7a1f64a01fd9d1e0fea002c37624faf" +dependencies = [ + "bitflags", + "cc", + "cfg-if 1.0.0", + "libc", + "memoffset 0.6.5", +] + +[[package]] +name = "nix" +version = "0.24.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fa52e972a9a719cecb6864fb88568781eb706bac2cd1d4f04a648542dbf78069" +dependencies = [ + "bitflags", + "cfg-if 1.0.0", + "libc", + "memoffset 0.6.5", +] + +[[package]] +name = "nix" +version = "0.25.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f346ff70e7dbfd675fe90590b92d59ef2de15a8779ae305ebcbfd3f0caf59be4" +dependencies = [ + "autocfg", + "bitflags", + "cfg-if 1.0.0", + "libc", + "memoffset 0.6.5", +] + +[[package]] +name = "nom" +version = "7.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a" +dependencies = [ + "memchr", + "minimal-lexical", +] + +[[package]] +name = "num-integer" +version = "0.1.45" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "225d3389fb3509a24c93f5c29eb6bde2586b98d9f016636dff58d7c6f7569cd9" +dependencies = [ + "autocfg", + "num-traits", +] + +[[package]] +name = "num-rational" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0638a1c9d0a3c0914158145bc76cff373a75a627e6ecbfb71cbe6f453a5a19b0" +dependencies = [ + "autocfg", + "num-integer", + "num-traits", +] + +[[package]] +name = "num-traits" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "578ede34cf02f8924ab9447f50c28075b4d3e5b269972345e7e0372b38c6cdcd" +dependencies = [ + "autocfg", +] + +[[package]] +name = "num_cpus" +version = "1.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" +dependencies = [ + "hermit-abi", + "libc", +] + +[[package]] +name = "num_enum" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f646caf906c20226733ed5b1374287eb97e3c2a5c227ce668c1f2ce20ae57c9" +dependencies = [ + "num_enum_derive", +] + +[[package]] +name = "num_enum_derive" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dcbff9bc912032c62bf65ef1d5aea88983b420f4f839db1e9b0c281a25c9c799" +dependencies = [ + "proc-macro-crate", + "proc-macro2", + "quote", + "syn 1.0.109", +] + +[[package]] +name = "objc" +version = "0.2.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "915b1b472bc21c53464d6c8461c9d3af805ba1ef837e1cac254428f4a77177b1" +dependencies = [ + "malloc_buf", +] + +[[package]] +name = "object-pool" +version = "0.5.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ee9a3e7196d09ec86002b939f1576e8e446d58def8fd48fe578e2c72d5328d68" +dependencies = [ + "parking_lot 0.11.2", +] + +[[package]] +name = "once_cell" +version = "1.18.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dd8b5dd2ae5ed71462c540258bedcb51965123ad7e7ccf4b9a8cafaa4a63576d" + +[[package]] +name = "osmesa-sys" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "88cfece6e95d2e717e0872a7f53a8684712ad13822a7979bc760b9c77ec0013b" +dependencies = [ + "shared_library", +] + +[[package]] +name = "parking_lot" +version = "0.11.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7d17b78036a60663b797adeaee46f5c9dfebb86948d1255007a1d6be0271ff99" +dependencies = [ + "instant", + "lock_api", + "parking_lot_core 0.8.6", +] + +[[package]] +name = "parking_lot" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" +dependencies = [ + "lock_api", + "parking_lot_core 0.9.8", +] + +[[package]] +name = "parking_lot_core" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60a2cfe6f0ad2bfc16aefa463b497d5c7a5ecd44a23efa72aa342d90177356dc" +dependencies = [ + "cfg-if 1.0.0", + "instant", + "libc", + "redox_syscall 0.2.16", + "smallvec", + "winapi", +] + +[[package]] +name = "parking_lot_core" +version = "0.9.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93f00c865fe7cabf650081affecd3871070f26767e7b2070a3ffae14c654b447" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "redox_syscall 0.3.5", + "smallvec", + "windows-targets", +] + +[[package]] +name = "percent-encoding" +version = "2.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" + +[[package]] +name = "pkg-config" +version = "0.3.27" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26072860ba924cbfa98ea39c8c19b4dd6a4a25423dbdf219c1eca91aa0cf6964" + +[[package]] +name = "png" +version = "0.17.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "59871cc5b6cce7eaccca5a802b4173377a1c2ba90654246789a8fa2334426d11" +dependencies = [ + "bitflags", + "crc32fast", + "fdeflate", + "flate2", + "miniz_oxide", +] + +[[package]] +name = "proc-macro-crate" +version = "1.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f4c021e1093a56626774e81216a4ce732a735e5bad4868a03f3ed65ca0c3919" +dependencies = [ + "once_cell", + "toml_edit", +] + +[[package]] +name = "proc-macro2" +version = "1.0.63" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b368fba921b0dce7e60f5e04ec15e565b3303972b42bcfde1d0713b881959eb" +dependencies = [ + "unicode-ident", +] + +[[package]] +name = "quote" +version = "1.0.29" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "573015e8ab27661678357f27dc26460738fd2b6c86e46f386fde94cb5d913105" +dependencies = [ + "proc-macro2", +] + +[[package]] +name = "rand" +version = "0.8.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +dependencies = [ + "rand_core", +] + +[[package]] +name = "rand_core" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" + +[[package]] +name = "rand_xorshift" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d25bf25ec5ae4a3f1b92f929810509a2f53d7dca2f50b794ff57e3face536c8f" +dependencies = [ + "rand_core", +] + +[[package]] +name = "raw-window-handle" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b800beb9b6e7d2df1fe337c9e3d04e3af22a124460fb4c30fcc22c9117cefb41" +dependencies = [ + "cty", +] + +[[package]] +name = "raw-window-handle" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2ff9a1f06a88b01621b7ae906ef0211290d1c8a168a15542486a8f61c0833b9" + +[[package]] +name = "rayon" +version = "1.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d2df5196e37bcc87abebc0053e20787d73847bb33134a69841207dd0a47f03b" +dependencies = [ + "either", + "rayon-core", +] + +[[package]] +name = "rayon-core" +version = "1.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4b8f95bd6966f5c87776639160a66bd8ab9895d9d4ab01ddba9fc60661aebe8d" +dependencies = [ + "crossbeam-channel", + "crossbeam-deque", + "crossbeam-utils 0.8.16", + "num_cpus", +] + +[[package]] +name = "redox_syscall" +version = "0.2.16" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a" +dependencies = [ + "bitflags", +] + +[[package]] +name = "redox_syscall" +version = "0.3.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "567664f262709473930a4bf9e51bf2ebf3348f2e748ccc50dea20646858f8f29" +dependencies = [ + "bitflags", +] + +[[package]] +name = "regex" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89089e897c013b3deb627116ae56a6955a72b8bed395c9526af31c9fe528b484" +dependencies = [ + "aho-corasick", + "memchr", + "regex-automata", + "regex-syntax", +] + +[[package]] +name = "regex-automata" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fa250384981ea14565685dea16a9ccc4d1c541a13f82b9c168572264d1df8c56" +dependencies = [ + "aho-corasick", + "memchr", + "regex-syntax", +] + +[[package]] +name = "regex-syntax" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2ab07dc67230e4a4718e70fd5c20055a4334b121f1f9db8fe63ef39ce9b8c846" + +[[package]] +name = "rltk" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "30587bc9361fc5600650d17ad6b9a91bb6a290f9d06a434dc48198d22ead7543" +dependencies = [ + "bracket-lib", +] + +[[package]] +name = "rust-llyrl" +version = "0.1.0" +dependencies = [ + "rltk", + "specs", + "specs-derive", +] + +[[package]] +name = "safe_arch" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1ff3d6d9696af502cc3110dacce942840fb06ff4514cad92236ecc455f2ce05" +dependencies = [ + "bytemuck", +] + +[[package]] +name = "safe_arch" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62a7484307bd40f8f7ccbacccac730108f2cae119a3b11c74485b48aa9ea650f" +dependencies = [ + "bytemuck", +] + +[[package]] +name = "scoped-tls" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1cf6437eb19a8f4a6cc0f7dca544973b0b78843adbfeb3683d1a94a0024a294" + +[[package]] +name = "scopeguard" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" + +[[package]] +name = "sctk-adwaita" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "61270629cc6b4d77ec1907db1033d5c2e1a404c412743621981a871dc9c12339" +dependencies = [ + "crossfont", + "log", + "smithay-client-toolkit 0.16.0", + "tiny-skia", +] + +[[package]] +name = "send_wrapper" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a0eddf2e8f50ced781f288c19f18621fa72a3779e3cb58dbf23b07469b0abeb4" + +[[package]] +name = "serde" +version = "1.0.166" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d01b7404f9d441d3ad40e6a636a7782c377d2abdbe4fa2440e2edcc2f4f10db8" + +[[package]] +name = "serde_derive" +version = "1.0.166" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5dd83d6dde2b6b2d466e14d9d1acce8816dedee94f735eac6395808b3483c6d6" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.23", +] + +[[package]] +name = "servo-fontconfig" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c7e3e22fe5fd73d04ebf0daa049d3efe3eae55369ce38ab16d07ddd9ac5c217c" +dependencies = [ + "libc", + "servo-fontconfig-sys", +] + +[[package]] +name = "servo-fontconfig-sys" +version = "5.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e36b879db9892dfa40f95da1c38a835d41634b825fbd8c4c418093d53c24b388" +dependencies = [ + "expat-sys", + "freetype-sys", + "pkg-config", +] + +[[package]] +name = "shared_library" +version = "0.1.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a9e7e0f2bfae24d8a5b5a66c5b257a83c7412304311512a0c054cd5e619da11" +dependencies = [ + "lazy_static", + "libc", +] + +[[package]] +name = "shred" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c5f08237e667ac94ad20f8878b5943d91a93ccb231428446c57c21c57779016d" +dependencies = [ + "arrayvec", + "hashbrown 0.7.2", + "mopa", + "rayon", + "smallvec", + "tynm", +] + +[[package]] +name = "shrev" +version = "1.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a5ea33232fdcf1bf691ca33450e5a94dde13e1a8cbb8caabc5e4f9d761e10b1a" + +[[package]] +name = "simd-adler32" +version = "0.3.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "238abfbb77c1915110ad968465608b68e869e0772622c9656714e73e5a1a522f" + +[[package]] +name = "slab" +version = "0.4.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6528351c9bc8ab22353f9d776db39a20288e8d6c37ef8cfe3317cf875eecfc2d" +dependencies = [ + "autocfg", +] + +[[package]] +name = "slotmap" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1e08e261d0e8f5c43123b7adf3e4ca1690d655377ac93a03b2c9d3e98de1342" +dependencies = [ + "version_check", +] + +[[package]] +name = "smallvec" +version = "1.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "62bb4feee49fdd9f707ef802e22365a35de4b7b299de4763d44bfea899442ff9" + +[[package]] +name = "smithay-client-toolkit" +version = "0.15.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a28f16a97fa0e8ce563b2774d1e732dd5d4025d2772c5dba0a41a0f90a29da3" +dependencies = [ + "bitflags", + "calloop 0.9.3", + "dlib", + "lazy_static", + "log", + "memmap2 0.3.1", + "nix 0.22.3", + "pkg-config", + "wayland-client", + "wayland-cursor", + "wayland-protocols", +] + +[[package]] +name = "smithay-client-toolkit" +version = "0.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f307c47d32d2715eb2e0ece5589057820e0e5e70d07c247d1063e844e107f454" +dependencies = [ + "bitflags", + "calloop 0.10.6", + "dlib", + "lazy_static", + "log", + "memmap2 0.5.10", + "nix 0.24.3", + "pkg-config", + "wayland-client", + "wayland-cursor", + "wayland-protocols", +] + +[[package]] +name = "specs" +version = "0.16.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fff28a29366aff703d5da8a7e2c8875dc8453ac1118f842cbc0fa70c7db51240" +dependencies = [ + "crossbeam-queue", + "hashbrown 0.7.2", + "hibitset", + "log", + "rayon", + "shred", + "shrev", + "tuple_utils", +] + +[[package]] +name = "specs-derive" +version = "0.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3e23e09360f3d2190fec4222cd9e19d3158d5da948c0d1ea362df617dd103511" +dependencies = [ + "proc-macro2", + "quote", + "syn 1.0.109", +] + +[[package]] +name = "strsim" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" + +[[package]] +name = "syn" +version = "1.0.109" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" +dependencies = [ + "proc-macro2", + "quote", + "unicode-ident", +] + +[[package]] +name = "syn" +version = "2.0.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "59fb7d6d8281a51045d62b8eb3a7d1ce347b76f312af50cd3dc0af39c87c1737" +dependencies = [ + "proc-macro2", + "quote", + "unicode-ident", +] + +[[package]] +name = "thiserror" +version = "1.0.41" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c16a64ba9387ef3fdae4f9c1a7f07a0997fce91985c0336f1ddc1822b3b37802" +dependencies = [ + "thiserror-impl", +] + +[[package]] +name = "thiserror-impl" +version = "1.0.41" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d14928354b01c4d6a4f0e549069adef399a284e7995c7ccca94e8a07a5346c59" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.23", +] + +[[package]] +name = "tiny-skia" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "642680569bb895b16e4b9d181c60be1ed136fa0c9c7f11d004daf053ba89bf82" +dependencies = [ + "arrayref", + "arrayvec", + "bytemuck", + "cfg-if 1.0.0", + "png", + "safe_arch 0.5.2", + "tiny-skia-path", +] + +[[package]] +name = "tiny-skia-path" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c114d32f0c2ee43d585367cb013dfaba967ab9f62b90d9af0d696e955e70fa6c" +dependencies = [ + "arrayref", + "bytemuck", +] + +[[package]] +name = "tokio-executor" +version = "0.1.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb2d1b8f4548dbf5e1f7818512e9c406860678f29c300cdf0ebac72d1a3a1671" +dependencies = [ + "crossbeam-utils 0.7.2", + "futures", +] + +[[package]] +name = "tokio-timer" +version = "0.2.13" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93044f2d313c95ff1cb7809ce9a7a05735b012288a888b62d4434fd58c94f296" +dependencies = [ + "crossbeam-utils 0.7.2", + "futures", + "slab", + "tokio-executor", +] + +[[package]] +name = "toml_datetime" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7cda73e2f1397b1262d6dfdcef8aafae14d1de7748d66822d3bfeeb6d03e5e4b" + +[[package]] +name = "toml_edit" +version = "0.19.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c500344a19072298cd05a7224b3c0c629348b78692bf48466c5238656e315a78" +dependencies = [ + "indexmap", + "toml_datetime", + "winnow", +] + +[[package]] +name = "tuple_utils" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "44834418e2c5b16f47bedf35c28e148db099187dd5feee6367fb2525863af4f1" + +[[package]] +name = "tynm" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b1b3ffc85961d3c7d038e30f5187622b33d971120c047ec8525b32602083645" +dependencies = [ + "nom", +] + +[[package]] +name = "ultraviolet" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca0b28b9a6ce66d47e3c5666aa738c5ec5223fcdd4c263f3edc98ab6fef618b3" +dependencies = [ + "wide", +] + +[[package]] +name = "unicode-ident" +version = "1.0.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "22049a19f4a68748a168c0fc439f9516686aa045927ff767eca0a85101fb6e73" + +[[package]] +name = "vec_map" +version = "0.8.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1bddf1187be692e79c5ffeab891132dfb0f236ed36a43c7ed39f1165ee20191" + +[[package]] +name = "version_check" +version = "0.9.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" + +[[package]] +name = "wasi" +version = "0.11.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" + +[[package]] +name = "wasm-bindgen" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7706a72ab36d8cb1f80ffbf0e071533974a60d0a308d01a5d0375bf60499a342" +dependencies = [ + "cfg-if 1.0.0", + "wasm-bindgen-macro", +] + +[[package]] +name = "wasm-bindgen-backend" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ef2b6d3c510e9625e5fe6f509ab07d66a760f0885d858736483c32ed7809abd" +dependencies = [ + "bumpalo", + "log", + "once_cell", + "proc-macro2", + "quote", + "syn 2.0.23", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-macro" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dee495e55982a3bd48105a7b947fd2a9b4a8ae3010041b9e0faab3f9cd028f1d" +dependencies = [ + "quote", + "wasm-bindgen-macro-support", +] + +[[package]] +name = "wasm-bindgen-macro-support" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "54681b18a46765f095758388f2d0cf16eb8d4169b639ab575a8f5693af210c7b" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.23", + "wasm-bindgen-backend", + "wasm-bindgen-shared", +] + +[[package]] +name = "wasm-bindgen-shared" +version = "0.2.87" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca6ad05a4870b2bf5fe995117d3728437bd27d7cd5f06f13c17443ef369775a1" + +[[package]] +name = "wasm-timer" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "aa3e01d234bb71760e685cfafa5e2c96f8ad877c161a721646356651069e26ac" +dependencies = [ + "futures", + "js-sys", + "send_wrapper", + "tokio-timer", + "wasm-bindgen", + "web-sys", +] + +[[package]] +name = "wayland-client" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3f3b068c05a039c9f755f881dc50f01732214f5685e379829759088967c46715" +dependencies = [ + "bitflags", + "downcast-rs", + "libc", + "nix 0.24.3", + "scoped-tls", + "wayland-commons", + "wayland-scanner", + "wayland-sys", +] + +[[package]] +name = "wayland-commons" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8691f134d584a33a6606d9d717b95c4fa20065605f798a3f350d78dced02a902" +dependencies = [ + "nix 0.24.3", + "once_cell", + "smallvec", + "wayland-sys", +] + +[[package]] +name = "wayland-cursor" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6865c6b66f13d6257bef1cd40cbfe8ef2f150fb8ebbdb1e8e873455931377661" +dependencies = [ + "nix 0.24.3", + "wayland-client", + "xcursor", +] + +[[package]] +name = "wayland-egl" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "402de949f81a012926d821a2d659f930694257e76dd92b6e0042ceb27be4107d" +dependencies = [ + "wayland-client", + "wayland-sys", +] + +[[package]] +name = "wayland-protocols" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b950621f9354b322ee817a23474e479b34be96c2e909c14f7bc0100e9a970bc6" +dependencies = [ + "bitflags", + "wayland-client", + "wayland-commons", + "wayland-scanner", +] + +[[package]] +name = "wayland-scanner" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8f4303d8fa22ab852f789e75a967f0a2cdc430a607751c0499bada3e451cbd53" +dependencies = [ + "proc-macro2", + "quote", + "xml-rs", +] + +[[package]] +name = "wayland-sys" +version = "0.29.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "be12ce1a3c39ec7dba25594b97b42cb3195d54953ddb9d3d95a7c3902bc6e9d4" +dependencies = [ + "dlib", + "lazy_static", + "pkg-config", +] + +[[package]] +name = "web-sys" +version = "0.3.64" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b85cbef8c220a6abc02aefd892dfc0fc23afb1c6a426316ec33253a3877249b" +dependencies = [ + "js-sys", + "wasm-bindgen", +] + +[[package]] +name = "wide" +version = "0.7.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "40018623e2dba2602a9790faba8d33f2ebdebf4b86561b83928db735f8784728" +dependencies = [ + "bytemuck", + "safe_arch 0.7.0", +] + +[[package]] +name = "winapi" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" +dependencies = [ + "winapi-i686-pc-windows-gnu", + "winapi-x86_64-pc-windows-gnu", +] + +[[package]] +name = "winapi-i686-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" + +[[package]] +name = "winapi-x86_64-pc-windows-gnu" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" + +[[package]] +name = "windows-sys" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2" +dependencies = [ + "windows_aarch64_msvc 0.36.1", + "windows_i686_gnu 0.36.1", + "windows_i686_msvc 0.36.1", + "windows_x86_64_gnu 0.36.1", + "windows_x86_64_msvc 0.36.1", +] + +[[package]] +name = "windows-sys" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" +dependencies = [ + "windows-targets", +] + +[[package]] +name = "windows-targets" +version = "0.48.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "05d4b17490f70499f20b9e791dcf6a299785ce8af4d709018206dc5b4953e95f" +dependencies = [ + "windows_aarch64_gnullvm", + "windows_aarch64_msvc 0.48.0", + "windows_i686_gnu 0.48.0", + "windows_i686_msvc 0.48.0", + "windows_x86_64_gnu 0.48.0", + "windows_x86_64_gnullvm", + "windows_x86_64_msvc 0.48.0", +] + +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91ae572e1b79dba883e0d315474df7305d12f569b400fcf90581b06062f7e1bc" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47" + +[[package]] +name = "windows_aarch64_msvc" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b2ef27e0d7bdfcfc7b868b317c1d32c641a6fe4629c171b8928c7b08d98d7cf3" + +[[package]] +name = "windows_i686_gnu" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6" + +[[package]] +name = "windows_i686_gnu" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "622a1962a7db830d6fd0a69683c80a18fda201879f0f447f065a3b7467daa241" + +[[package]] +name = "windows_i686_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024" + +[[package]] +name = "windows_i686_msvc" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4542c6e364ce21bf45d69fdd2a8e455fa38d316158cfd43b3ac1c5b1b19f8e00" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1" + +[[package]] +name = "windows_x86_64_gnu" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca2b8a661f7628cbd23440e50b05d705db3686f894fc9580820623656af974b1" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7896dbc1f41e08872e9d5e8f8baa8fdd2677f29468c4e156210174edc7f7b953" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680" + +[[package]] +name = "windows_x86_64_msvc" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a515f5799fe4961cb532f983ce2b23082366b898e52ffbce459c86f67c8378a" + +[[package]] +name = "winit" +version = "0.26.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9b43cc931d58b99461188607efd7acb2a093e65fc621f54cad78517a6063e73a" +dependencies = [ + "bitflags", + "cocoa", + "core-foundation 0.9.3", + "core-graphics 0.22.3", + "core-video-sys", + "dispatch", + "instant", + "lazy_static", + "libc", + "log", + "mio", + "ndk 0.5.0", + "ndk-glue 0.5.2", + "ndk-sys 0.2.2", + "objc", + "parking_lot 0.11.2", + "percent-encoding", + "raw-window-handle 0.4.3", + "smithay-client-toolkit 0.15.4", + "wasm-bindgen", + "wayland-client", + "wayland-protocols", + "web-sys", + "winapi", + "x11-dl", +] + +[[package]] +name = "winit" +version = "0.27.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bb796d6fbd86b2fd896c9471e6f04d39d750076ebe5680a3958f00f5ab97657c" +dependencies = [ + "bitflags", + "cocoa", + "core-foundation 0.9.3", + "core-graphics 0.22.3", + "dispatch", + "instant", + "libc", + "log", + "mio", + "ndk 0.7.0", + "ndk-glue 0.7.0", + "objc", + "once_cell", + "parking_lot 0.12.1", + "percent-encoding", + "raw-window-handle 0.4.3", + "raw-window-handle 0.5.2", + "sctk-adwaita", + "smithay-client-toolkit 0.16.0", + "wasm-bindgen", + "wayland-client", + "wayland-protocols", + "web-sys", + "windows-sys 0.36.1", + "x11-dl", +] + +[[package]] +name = "winnow" +version = "0.4.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ca0ace3845f0d96209f0375e6d367e3eb87eb65d27d445bdc9f1843a26f39448" +dependencies = [ + "memchr", +] + +[[package]] +name = "wio" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5d129932f4644ac2396cb456385cbf9e63b5b30c6e8dc4820bdca4eb082037a5" +dependencies = [ + "winapi", +] + +[[package]] +name = "x11-dl" +version = "2.21.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "38735924fedd5314a6e548792904ed8c6de6636285cb9fec04d5b1db85c1516f" +dependencies = [ + "libc", + "once_cell", + "pkg-config", +] + +[[package]] +name = "xcursor" +version = "0.3.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "463705a63313cd4301184381c5e8042f0a7e9b4bb63653f216311d4ae74690b7" +dependencies = [ + "nom", +] + +[[package]] +name = "xml-rs" +version = "0.8.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a56c84a8ccd4258aed21c92f70c0f6dea75356b6892ae27c24139da456f9336" diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..3c7cc09 --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,11 @@ +[package] +name = "rust-llyrl" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +rltk = { version = "0.8.7" } +specs = "0.16.1" +specs-derive = "0.4.1" diff --git a/resources/backing.fs b/resources/backing.fs new file mode 100644 index 0000000..23016a3 --- /dev/null +++ b/resources/backing.fs @@ -0,0 +1,12 @@ +#version 330 core +out vec4 FragColor; + +in vec2 TexCoords; + +uniform sampler2D screenTexture; + +void main() +{ + vec3 col = texture(screenTexture, TexCoords).rgb; + FragColor = vec4(col, 1.0); +} \ No newline at end of file diff --git a/resources/backing.vs b/resources/backing.vs new file mode 100644 index 0000000..2a6ddb5 --- /dev/null +++ b/resources/backing.vs @@ -0,0 +1,11 @@ +#version 330 core +layout (location = 0) in vec2 aPos; +layout (location = 1) in vec2 aTexCoords; + +out vec2 TexCoords; + +void main() +{ + TexCoords = aTexCoords; + gl_Position = vec4(aPos.x, aPos.y, 0.0, 1.0); +} diff --git a/resources/console_no_bg.fs b/resources/console_no_bg.fs new file mode 100644 index 0000000..728f0de --- /dev/null +++ b/resources/console_no_bg.fs @@ -0,0 +1,17 @@ +#version 330 core +out vec4 FragColor; + +in vec3 ourColor; +in vec2 TexCoord; +in vec3 ourBackground; + +// texture sampler +uniform sampler2D texture1; + +void main() +{ + vec4 original = texture(texture1, TexCoord); + if (original.r < 0.1f || original.g < 0.1f || original.b < 0.1f) discard; + vec4 fg = original * vec4(ourColor, 1.f); + FragColor = fg; +} diff --git a/resources/console_no_bg.vs b/resources/console_no_bg.vs new file mode 100644 index 0000000..ec9300b --- /dev/null +++ b/resources/console_no_bg.vs @@ -0,0 +1,17 @@ +#version 330 core +layout (location = 0) in vec3 aPos; +layout (location = 1) in vec3 aColor; +layout (location = 2) in vec3 bColor; +layout (location = 3) in vec2 aTexCoord; + +out vec3 ourColor; +out vec3 ourBackground; +out vec2 TexCoord; + +void main() +{ + gl_Position = vec4(aPos, 1.0); + ourColor = aColor; + ourBackground = bColor; + TexCoord = vec2(aTexCoord.x, aTexCoord.y); +} \ No newline at end of file diff --git a/resources/console_with_bg.fs b/resources/console_with_bg.fs new file mode 100644 index 0000000..4b5418b --- /dev/null +++ b/resources/console_with_bg.fs @@ -0,0 +1,16 @@ +#version 330 core +out vec4 FragColor; + +in vec3 ourColor; +in vec2 TexCoord; +in vec3 ourBackground; + +// texture sampler +uniform sampler2D texture1; + +void main() +{ + vec4 original = texture(texture1, TexCoord); + vec4 fg = original.r > 0.1f || original.g > 0.1f || original.b > 0.1f ? original * vec4(ourColor, 1.f) : vec4(ourBackground, 1.f); + FragColor = fg; +} diff --git a/resources/console_with_bg.vs b/resources/console_with_bg.vs new file mode 100644 index 0000000..ec9300b --- /dev/null +++ b/resources/console_with_bg.vs @@ -0,0 +1,17 @@ +#version 330 core +layout (location = 0) in vec3 aPos; +layout (location = 1) in vec3 aColor; +layout (location = 2) in vec3 bColor; +layout (location = 3) in vec2 aTexCoord; + +out vec3 ourColor; +out vec3 ourBackground; +out vec2 TexCoord; + +void main() +{ + gl_Position = vec4(aPos, 1.0); + ourColor = aColor; + ourBackground = bColor; + TexCoord = vec2(aTexCoord.x, aTexCoord.y); +} \ No newline at end of file diff --git a/resources/example_tiles.jpg b/resources/example_tiles.jpg new file mode 100644 index 0000000000000000000000000000000000000000..ca8aecd79d5a2f953b0b61759d2a3cb73553743c GIT binary patch literal 1928 zcmex=C5bm;@P_1sVSzVUS{A zWME=uWIzHe9E_~&Y#=#C3^_&?CT2F)|F;-;m>C(E1egUF7#P1635|F;-87#SHDS(##(CX^jIH0^`Kv`c^t8(k6bvnPoup8uN3 zdzQoOcC$(De9dal+DX5r?JEyHy7i?WYs0j^3I=*rE}MJLSZlnvrP*9)P`d19zObI9 z!JFGlQ;)?~z+ENqbN9)~Vj>wq*9LF-WY|P&>Z$!*OZFPrK&N6E*YM%dy4vUIYuj-pBt8 z2VO07u70NW$SnCkL*s>@zOP4oLvw%MhUHXnTnRk7r!vVCio|E9z}ce=`h>v$BMeG{ zj0}vRdH|kEK?%Vyu&`0U!7*{dLP+8SWgvm5X%nI^c~)r`do=$3bGm5?&(C8O$IhOy zy*;l}cO}bKE|%g<=KkuFOJV}pyB+5IzQvn%-#Y&P5e7Ly%(SLx$Pnl_5jkrK{D^kj zA>OuQd&{Xsv#wcBdc8-cG6Yq0@0vg~-O z*6tP9zZ+zUA}B#KG9#5MV1GC|1U4p4m)p24bAPq+ e!{<_AiWQ3POsyPGE^XvKC{@L(5Pm=J|4jhmu;NKR8IGcYt{U|?W`Vg?YH#=yWJ2oeB^3NtV;a5zt6U;tqT1_luZ1_l<8 z7y|=?7?cfCC(6LU=+3~vzzZ^3H#t8yH#M&WWEx0P$hjyru_QG`p**uBL&4qCHvl9f z09Klro0y)en_iTe0uo~cxkaP6q%tQ}p*TM$Gewh2BP~5SKPSIPK?6+b7NsX8Dj4b+ zfPsPm1_LIgsmZ00gik9>A;K`22uN#1aY15oW?s62p&8T)O)iZ}Y=TfR-O{|w5{1mX zB*Tp8a>0 z=^x`+gn6-%kr4@T@o`BBF>#4;VDtVp-1~O+-r0X(^O#rs-^dBFH#{jRH6k@JE_0EBZ{NJU{xyKy#=e4aBjbt(^H!|rNJ@-Lhz*NPjf_Z2PEYAzU}!jd_MhRm zZ-)QQ!j-bDc-#>m6&oEE6&4p6m6Q;h+QHD!aJIqg-nVb}yw08#V)#?KV%|J%kj*i1 zDGA95p;3{sF|lA5o;5t{b?=_nSwm!HF-Zy0aq)4HVJWHcG0`9gq6Q2o@S-B)6QdJS zq7tGKk`rSfY79YvX9x*Az7>x;5)VpEe-!V)?d7z~q=Kqe)DXhDYmrQ9p- zfqa=57aN@vA0Hkc8w!z4qH-Ee>KcQ7(A8h-OS+wJAmeb&p+u%1VV zfxn)=n2F)PB~vluKc?dUmO>2w>-n~QDE14A2=NaJ4DtyI^a~9wW@7keS$y^CzkgS+ z7K7C=ZTr8EW!wKXEZaU5`}lkN`3C!id4>9hg#;BdG5oQ-3QALd&t3(q<=gh7*vHq` zJJ3IvDe$*{U?@nQzlmaGI)T-^RF)aodA6+qM;l2Kfd0dHRKUd4`6Bg%v~6l;zc{mXI_BR?4#NadDte zps%-|ho6scaFBm!F*r?WPPuw@iY7Qs)o)v~hI`xBVt=22uz=7Y4_{v<|9^pCn=P+u zPMM;4)e@AZAj&=z`-KO22l)s2c!h-o`UZfMp#}^n@O=CNgMETS{Q`UgLxaFZSr%J@ z0?!f>czoL)6$gg|ga&&D2m6PGgn9-RGcZ^d7lTYH2GN2H|LeK8-2?eDD8S!0JTTBF z#6JM+dd;g-EQ_xe7hf&5oN`rDfZ=~V+cw5EtlJ(I`+NI)1qS#A`T7R>1Oyc`XkNWK zr5I#u@sz6|m4E8DZCk?(R{W?qI5^1D%g5K(FD%GE+^?8{K~u9BqPSR76J$NeA0hrh zem;Iap+12D!NGnIzgmLqhWmrRn2~|e@|$M2m!_syx2B~fG)-wRG5k+rn!@;xY0Cd3 zaGKiwK|@AfUQSj{T1i?#QC40~gNfl=(v)}a{{4IRZVFfp)As-SS+@UQ%d-80hNPT~ zw4A(@qLhN1tQ<(~pQLw?H1!UwmT&t94OwYf8Ce-Q8CiK*1w{q0dH))cmYhvG`wy&! zdHetUoFIE;%NkG!n_O)xd zxBu5*lK-NhsHh+#EhnWQ1M*S&#$eWECOGPy+_! zSs57xIcZr1d09D7h=4qiG$jcXcuA1J)xwqc~`BGL^PF6`qQC417US38{gF#|RQqq)nQ>MI|l9aSW0-UC{Gp=Rb{zXGp zMqW-{RzX%qTAoSv14!kPq$wa3c%9M9-fADKCGB756lgJW~kPyg{NJ;{w msd|vB1Q;0V5%@n68zesL_zVmTpcWVigPH&i3=9k)%m4txe}~`z literal 0 HcmV?d00001 diff --git a/resources/mltest.xp b/resources/mltest.xp new file mode 100644 index 0000000000000000000000000000000000000000..640adc793209be354d4e702025cd133137caa6e6 GIT binary patch literal 62 zcmb2|=3oE=?%)6a|F2hLV`Jk}NMlTLXA}5ge@baGE4Mo<+lmYIS)1o1gc&MCG<(XH PMlk5b{gax(#J~UmJ+>0u literal 0 HcmV?d00001 diff --git a/resources/nyan.xp b/resources/nyan.xp new file mode 100644 index 0000000000000000000000000000000000000000..f27c58d6d90ba072880479504d8c606380e6d7f3 GIT binary patch literal 393 zcmb2|=3oE=?zgip<~AD$w5|2Ku-qp66~~#2rbfP3%HLn%m3Y>rUaq_-zROU;+3Cn{*pXIe~ zUb*y{(8a$S7rj+yUzr-4mweZ2n)0>0y{W(Yx9@u&VZJx@*PXJZv&zrjy`jD9$|WP^ zska+gvhU7XugW`3H?Q)mS>!66R{sgVQkLwjtc_3FtoI?$((~@CzQ(gs2jo}V$*py} p^h&k1|8-dP`K#wM?oU$RJG(vbe)0!7x419-ll(TZIoL2T005hw!{`72 literal 0 HcmV?d00001 diff --git a/resources/scanlines.fs b/resources/scanlines.fs new file mode 100644 index 0000000..57b8795 --- /dev/null +++ b/resources/scanlines.fs @@ -0,0 +1,26 @@ +#version 330 core +out vec4 FragColor; + +in vec2 TexCoords; + +uniform sampler2D screenTexture; +uniform vec3 screenSize; +uniform bool screenBurn; + +void main() +{ + vec3 col = texture(screenTexture, TexCoords).rgb; + float scanLine = mod(gl_FragCoord.y, 2.0) * 0.25; + vec3 scanColor = col.rgb - scanLine; + + if (col.r < 0.1f && col.g < 0.1f && col.b < 0.1f) { + if (screenBurn) { + float dist = (1.0 - distance(vec2(gl_FragCoord.x / screenSize.x, gl_FragCoord.y / screenSize.y), vec2(0.5,0.5))) * 0.2; + FragColor = vec4(0.0, dist, dist, 1.0); + } else { + FragColor = vec4(0.0, 0.0, 0.0, 1.0); + } + } else { + FragColor = vec4(scanColor, 1.0); + } +} \ No newline at end of file diff --git a/resources/scanlines.vs b/resources/scanlines.vs new file mode 100644 index 0000000..2a6ddb5 --- /dev/null +++ b/resources/scanlines.vs @@ -0,0 +1,11 @@ +#version 330 core +layout (location = 0) in vec2 aPos; +layout (location = 1) in vec2 aTexCoords; + +out vec2 TexCoords; + +void main() +{ + TexCoords = aTexCoords; + gl_Position = vec4(aPos.x, aPos.y, 0.0, 1.0); +} diff --git a/resources/terminal10x10_gs_tc.png b/resources/terminal10x10_gs_tc.png new file mode 100644 index 0000000000000000000000000000000000000000..5e0cdc92fb3881ead60f4b856ee19c00d333855e GIT binary patch literal 8804 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 e#Zm%oT_y4|PSkCQXFg>xGi|Lj, + pub range: i32, + pub dirty: bool, +} + +#[derive(Component, Debug)] +pub struct Name { + pub name: String, +} + +#[derive(Component, Debug)] +pub struct BlocksTile {} + +#[derive(Component, Debug)] +pub struct CombatStats { + pub max_hp: i32, + pub hp: i32, + pub defence: i32, + pub power: i32, +} + +#[derive(Component, Debug, Clone)] +pub struct WantsToMelee { + pub target: Entity, +} + +#[derive(Component, Debug)] +pub struct SufferDamage { + pub amount: Vec, +} + +impl SufferDamage { + pub fn new_damage(store: &mut WriteStorage, victim: Entity, amount: i32) { + if let Some(suffering) = store.get_mut(victim) { + suffering.amount.push(amount); + } else { + let dmg = SufferDamage { amount: vec![amount] }; + store.insert(victim, dmg).expect("Unable to insert damage."); + } + } +} diff --git a/src/damage_system.rs b/src/damage_system.rs new file mode 100644 index 0000000..ecda203 --- /dev/null +++ b/src/damage_system.rs @@ -0,0 +1,50 @@ +use super::{CombatStats, GameLog, Name, Player, SufferDamage}; +use rltk::console; +use specs::prelude::*; + +pub struct DamageSystem {} + +impl<'a> System<'a> for DamageSystem { + type SystemData = (WriteStorage<'a, CombatStats>, WriteStorage<'a, SufferDamage>); + + fn run(&mut self, data: Self::SystemData) { + let (mut stats, mut damage) = data; + + for (mut stats, damage) in (&mut stats, &damage).join() { + stats.hp -= damage.amount.iter().sum::(); + } + + damage.clear(); + } +} + +pub fn delete_the_dead(ecs: &mut World) { + let mut dead: Vec = Vec::new(); + // Using scope to make borrow checker happy + { + let combat_stats = ecs.read_storage::(); + let players = ecs.read_storage::(); + let names = ecs.read_storage::(); + let entities = ecs.entities(); + let mut log = ecs.write_resource::(); + for (entity, stats) in (&entities, &combat_stats).join() { + if stats.hp < 1 { + let player = players.get(entity); + match player { + None => { + let victim_name = names.get(entity); + if let Some(victim_name) = victim_name { + log.entries.push(format!("{} died!", &victim_name.name)); + } + dead.push(entity) + } + Some(_) => console::log("You died."), + } + } + } + } + + for victim in dead { + ecs.delete_entity(victim).expect("Unable to delete."); + } +} diff --git a/src/gamelog.rs b/src/gamelog.rs new file mode 100644 index 0000000..dbe28c0 --- /dev/null +++ b/src/gamelog.rs @@ -0,0 +1,3 @@ +pub struct GameLog { + pub entries: Vec, +} diff --git a/src/gui.rs b/src/gui.rs new file mode 100644 index 0000000..6fdd7aa --- /dev/null +++ b/src/gui.rs @@ -0,0 +1,112 @@ +use super::{CombatStats, GameLog, Map, Name, Player, Point, Position}; +use rltk::{Rltk, RGB}; +use specs::prelude::*; + +pub fn draw_ui(ecs: &World, ctx: &mut Rltk) { + ctx.draw_box(0, 43, 79, 6, RGB::named(rltk::WHITE), RGB::named(rltk::BLACK)); + + // Render stats + let combat_stats = ecs.read_storage::(); + let players = ecs.read_storage::(); + for (_player, stats) in (&players, &combat_stats).join() { + let health = format!(" HP: {} / {} ", stats.hp, stats.max_hp); + ctx.print_color(12, 43, RGB::named(rltk::YELLOW), RGB::named(rltk::BLACK), &health); + ctx.draw_bar_horizontal(28, 43, 51, stats.hp, stats.max_hp, RGB::named(rltk::RED), RGB::named(rltk::BLACK)); + } + + // Render message log + let log = ecs.fetch::(); + let mut y = 44; + for s in log.entries.iter().rev() { + if y < 49 { + ctx.print(2, y, s); + } + y += 1; + } + + // Render mouse cursor + let mouse_pos = ctx.mouse_pos(); + ctx.set_bg(mouse_pos.0, mouse_pos.1, RGB::named(rltk::MAGENTA)); + + draw_tooltips(ecs, ctx); +} + +fn draw_tooltips(ecs: &World, ctx: &mut Rltk) { + let map = ecs.fetch::(); + let names = ecs.read_storage::(); + let positions = ecs.read_storage::(); + + let mouse_pos = ctx.mouse_pos(); + if mouse_pos.0 >= map.width || mouse_pos.1 >= map.height { + return; + } + let mut tooltip: Vec = Vec::new(); + for (name, position) in (&names, &positions).join() { + let idx = map.xy_idx(position.x, position.y); + if position.x == mouse_pos.0 && position.y == mouse_pos.1 && map.visible_tiles[idx] { + tooltip.push(name.name.to_string()); + } + } + + if !tooltip.is_empty() { + let mut width: i32 = 0; + for s in tooltip.iter() { + if width < s.len() as i32 { + width = s.len() as i32; + } + width += 3; + + if mouse_pos.0 > 40 { + let arrow_pos = Point::new(mouse_pos.0 - 2, mouse_pos.1); + let left_x = mouse_pos.0 - width; + let mut y = mouse_pos.1; + for s in tooltip.iter() { + ctx.print_color(left_x, y, RGB::named(rltk::WHITE), RGB::named(rltk::GREY), s); + let padding = (width - s.len() as i32) - 1; + for i in 0..padding { + ctx.print_color( + arrow_pos.x - i, + y, + RGB::named(rltk::WHITE), + RGB::named(rltk::GREY), + &" ".to_string(), + ); + } + y += 1; + } + ctx.print_color( + arrow_pos.x, + arrow_pos.y, + RGB::named(rltk::WHITE), + RGB::named(rltk::GREY), + &"->".to_string(), + ); + } else { + let arrow_pos = Point::new(mouse_pos.0 + 1, mouse_pos.1); + let left_x = mouse_pos.0 + 3; + let mut y = mouse_pos.1; + for s in tooltip.iter() { + ctx.print_color(left_x + 1, y, RGB::named(rltk::WHITE), RGB::named(rltk::GREY), s); + let padding = (width - s.len() as i32) - 1; + for i in 0..padding { + ctx.print_color( + arrow_pos.x + 1 + i, + y, + RGB::named(rltk::WHITE), + RGB::named(rltk::GREY), + &" ".to_string(), + ); + } + y += 1; + } + ctx.print_color( + arrow_pos.x, + arrow_pos.y, + RGB::named(rltk::WHITE), + RGB::named(rltk::GREY), + &"<-".to_string(), + ); + } + } + } +} diff --git a/src/main.rs b/src/main.rs new file mode 100644 index 0000000..45ae341 --- /dev/null +++ b/src/main.rs @@ -0,0 +1,176 @@ +use rltk::{GameState, Point, Rltk, RGB}; +use specs::prelude::*; + +mod components; +pub use components::*; +mod map; +pub use map::*; +mod player; +use player::*; +mod rect; +pub use rect::Rect; +mod gamelog; +use gamelog::GameLog; +mod gui; +mod visibility_system; +use visibility_system::VisibilitySystem; +mod monster_ai_system; +use monster_ai_system::MonsterAI; +mod map_indexing_system; +use map_indexing_system::MapIndexingSystem; +mod damage_system; +use damage_system::*; +mod melee_combat_system; +use melee_combat_system::MeleeCombatSystem; + +#[derive(PartialEq, Copy, Clone)] +pub enum RunState { + AwaitingInput, + PreRun, + PlayerTurn, + MonsterTurn, +} + +pub struct State { + pub ecs: World, +} + +impl State { + fn run_systems(&mut self) { + let mut vis = VisibilitySystem {}; + vis.run_now(&self.ecs); + let mut mob = MonsterAI {}; + mob.run_now(&self.ecs); + let mut mapindex = MapIndexingSystem {}; + mapindex.run_now(&self.ecs); + let mut melee_system = MeleeCombatSystem {}; + melee_system.run_now(&self.ecs); + let mut damage_system = DamageSystem {}; + damage_system.run_now(&self.ecs); + self.ecs.maintain(); + } +} + +impl GameState for State { + fn tick(&mut self, ctx: &mut Rltk) { + ctx.cls(); + + let mut new_runstate; + { + let runstate = self.ecs.fetch::(); + new_runstate = *runstate; + } + + match new_runstate { + RunState::PreRun => { + self.run_systems(); + new_runstate = RunState::AwaitingInput; + } + RunState::AwaitingInput => { + new_runstate = player_input(self, ctx); + } + RunState::PlayerTurn => { + self.run_systems(); + new_runstate = RunState::MonsterTurn; + } + RunState::MonsterTurn => { + self.run_systems(); + new_runstate = RunState::AwaitingInput; + } + } + + { + let mut runwriter = self.ecs.write_resource::(); + *runwriter = new_runstate; + } + + damage_system::delete_the_dead(&mut self.ecs); + draw_map(&self.ecs, ctx); + + let positions = self.ecs.read_storage::(); + let renderables = self.ecs.read_storage::(); + let map = self.ecs.fetch::(); + + for (pos, render) in (&positions, &renderables).join() { + let idx = map.xy_idx(pos.x, pos.y); + if map.visible_tiles[idx] { + ctx.set(pos.x, pos.y, render.fg, render.bg, render.glyph); + } + } + + gui::draw_ui(&self.ecs, ctx); + } +} + +fn main() -> rltk::BError { + use rltk::RltkBuilder; + let mut context = RltkBuilder::simple80x50() + .with_gutter(0) + .with_tile_dimensions(16, 16) + //.with_fitscreen(true) + .with_title("Roguelike Tutorial") + .build()?; + context.with_post_scanlines(true); + let mut gs = State { ecs: World::new() }; + + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + gs.ecs.register::(); + + let map = Map::new_map_rooms_and_corridors(); + let (player_x, player_y) = map.rooms[0].centre(); + + let player_entity = gs + .ecs + .create_entity() + .with(Position { x: player_x, y: player_y }) + .with(Renderable { glyph: rltk::to_cp437('@'), fg: RGB::named(rltk::YELLOW), bg: RGB::named(rltk::BLACK) }) + .with(Player {}) + .with(Viewshed { visible_tiles: Vec::new(), range: 8, dirty: true }) + .with(Name { name: "Player".to_string() }) + .with(CombatStats { max_hp: 30, hp: 30, defence: 2, power: 5 }) + .build(); + + let mut rng = rltk::RandomNumberGenerator::new(); + for (i, room) in map.rooms.iter().skip(1).enumerate() { + let (x, y) = room.centre(); + let glyph: rltk::FontCharType; + let name: String; + let roll = rng.roll_dice(1, 2); + match roll { + 1 => { + glyph = rltk::to_cp437('g'); + name = "Goblin".to_string(); + } + _ => { + glyph = rltk::to_cp437('o'); + name = "Orc".to_string(); + } + } + gs.ecs + .create_entity() + .with(Position { x, y }) + .with(Renderable { glyph: glyph, fg: RGB::named(rltk::RED), bg: RGB::named(rltk::BLACK) }) + .with(Viewshed { visible_tiles: Vec::new(), range: 8, dirty: true }) + .with(Monster {}) + .with(Name { name: format!("{} #{}", &name, i) }) + .with(BlocksTile {}) + .with(CombatStats { max_hp: 16, hp: 16, defence: 1, power: 4 }) + .build(); + } + + gs.ecs.insert(map); + gs.ecs.insert(Point::new(player_x, player_y)); + gs.ecs.insert(player_entity); + gs.ecs.insert(gamelog::GameLog { entries: vec!["Here's your welcome message.".to_string()] }); + gs.ecs.insert(RunState::PreRun); + + rltk::main_loop(context, gs) +} diff --git a/src/map.rs b/src/map.rs new file mode 100644 index 0000000..613deb0 --- /dev/null +++ b/src/map.rs @@ -0,0 +1,224 @@ +use super::Rect; +use rltk::{Algorithm2D, BaseMap, Point, RandomNumberGenerator, Rltk, RGB}; +use specs::prelude::*; +use std::cmp::{max, min}; + +#[derive(PartialEq, Copy, Clone)] +pub enum TileType { + Wall, + Floor, +} + +pub const MAPWIDTH: usize = 80; +pub const MAPHEIGHT: usize = 43; +const MAPCOUNT: usize = MAPHEIGHT * MAPWIDTH; + +#[derive(Default)] +pub struct Map { + pub tiles: Vec, + pub rooms: Vec, + pub width: i32, + pub height: i32, + pub revealed_tiles: Vec, + pub visible_tiles: Vec, + pub blocked: Vec, + pub tile_content: Vec>, +} + +impl Map { + pub fn xy_idx(&self, x: i32, y: i32) -> usize { + (y as usize) * (self.width as usize) + (x as usize) + } + + fn apply_room_to_map(&mut self, room: &Rect) { + for y in room.y1 + 1..=room.y2 { + for x in room.x1 + 1..=room.x2 { + let idx = self.xy_idx(x, y); + self.tiles[idx] = TileType::Floor; + } + } + } + + fn apply_horizontal_tunnel(&mut self, x1: i32, x2: i32, y: i32) { + for x in min(x1, x2)..=max(x1, x2) { + let idx = self.xy_idx(x, y); + if idx > 0 && idx < (self.width as usize) * (self.height as usize) { + self.tiles[idx as usize] = TileType::Floor; + } + } + } + + fn apply_vertical_tunnel(&mut self, y1: i32, y2: i32, x: i32) { + for y in min(y1, y2)..=max(y1, y2) { + let idx = self.xy_idx(x, y); + if idx > 0 && idx < (self.width as usize) * (self.height as usize) { + self.tiles[idx as usize] = TileType::Floor; + } + } + } + + /// Takes an index, and calculates if it can be entered. + fn is_exit_valid(&self, x: i32, y: i32) -> bool { + if x < 1 || x > self.width - 1 || y < 1 || y > self.height - 1 { + return false; + } + let idx = self.xy_idx(x, y); + !self.blocked[idx] + } + + pub fn populate_blocked(&mut self) { + for (i, tile) in self.tiles.iter_mut().enumerate() { + self.blocked[i] = *tile == TileType::Wall; + } + } + + pub fn clear_content_index(&mut self) { + for content in self.tile_content.iter_mut() { + content.clear(); + } + } + + /// Makes a procgen map out of rooms and corridors, and returns the rooms and the map. + pub fn new_map_rooms_and_corridors() -> Map { + let mut map = Map { + tiles: vec![TileType::Wall; MAPCOUNT], + rooms: Vec::new(), + width: MAPWIDTH as i32, + height: MAPHEIGHT as i32, + revealed_tiles: vec![false; MAPCOUNT], + visible_tiles: vec![false; MAPCOUNT], + blocked: vec![false; MAPCOUNT], + tile_content: vec![Vec::new(); MAPCOUNT], + }; + + const MAX_ROOMS: i32 = 30; + const MIN_SIZE: i32 = 6; + const MAX_SIZE: i32 = 10; + + let mut rng = RandomNumberGenerator::new(); + + for _i in 0..MAX_ROOMS { + let w = rng.range(MIN_SIZE, MAX_SIZE); + let h = rng.range(MIN_SIZE, MAX_SIZE); + let x = rng.roll_dice(1, map.width - w - 1) - 1; + let y = rng.roll_dice(1, map.height - h - 1) - 1; + let new_room = Rect::new(x, y, w, h); + let mut ok = true; + for other_room in map.rooms.iter() { + if new_room.intersect(other_room) { + ok = false; + } + } + if ok { + map.apply_room_to_map(&new_room); + + if !map.rooms.is_empty() { + let (new_x, new_y) = new_room.centre(); + let (prev_x, prev_y) = map.rooms[map.rooms.len() - 1].centre(); + if rng.range(0, 2) == 1 { + map.apply_horizontal_tunnel(prev_x, new_x, prev_y); + map.apply_vertical_tunnel(prev_y, new_y, prev_x); + } else { + map.apply_vertical_tunnel(prev_y, new_y, prev_x); + map.apply_horizontal_tunnel(prev_x, new_x, prev_y); + } + } + + map.rooms.push(new_room); + } + } + + map + } +} + +impl Algorithm2D for Map { + fn dimensions(&self) -> Point { + Point::new(self.width, self.height) + } +} + +impl BaseMap for Map { + fn is_opaque(&self, idx: usize) -> bool { + self.tiles[idx as usize] == TileType::Wall + } + + fn get_pathing_distance(&self, idx1: usize, idx2: usize) -> f32 { + let w = self.width as usize; + let p1 = Point::new(idx1 % w, idx1 / w); + let p2 = Point::new(idx2 % w, idx2 / w); + rltk::DistanceAlg::Pythagoras.distance2d(p1, p2) + } + + /// Evaluate every possible exit from a given tile in a cardinal direction, and return it as a vector. + fn get_available_exits(&self, idx: usize) -> rltk::SmallVec<[(usize, f32); 10]> { + let mut exits = rltk::SmallVec::new(); + let x = (idx as i32) % self.width; + let y = (idx as i32) / self.width; + let w = self.width as usize; + + // Cardinal directions + if self.is_exit_valid(x - 1, y) { + exits.push((idx - 1, 1.0)); + } + if self.is_exit_valid(x + 1, y) { + exits.push((idx + 1, 1.0)); + } + if self.is_exit_valid(x, y - 1) { + exits.push((idx - w, 1.0)); + } + if self.is_exit_valid(x, y + 1) { + exits.push((idx + w, 1.0)); + } + + // Diagonals + if self.is_exit_valid(x - 1, y - 1) { + exits.push((idx - w - 1, 1.45)); + } + if self.is_exit_valid(x + 1, y - 1) { + exits.push((idx - w + 1, 1.45)); + } + if self.is_exit_valid(x - 1, y + 1) { + exits.push((idx - w - 1, 1.45)); + } + if self.is_exit_valid(x + 1, y + 1) { + exits.push((idx + w + 1, 1.45)); + } + + exits + } +} + +pub fn draw_map(ecs: &World, ctx: &mut Rltk) { + let map = ecs.fetch::(); + + let mut y = 0; + let mut x = 0; + for (idx, tile) in map.tiles.iter().enumerate() { + if map.revealed_tiles[idx] { + let glyph; + let mut fg; + match tile { + TileType::Floor => { + glyph = rltk::to_cp437('.'); + fg = RGB::from_f32(0.0, 1.0, 0.5); + } + TileType::Wall => { + glyph = rltk::to_cp437('#'); + fg = RGB::from_f32(0.0, 1.0, 0.0); + } + } + if !map.visible_tiles[idx] { + fg = fg.to_greyscale(); + } + ctx.set(x, y, fg, RGB::from_f32(0.0, 0.0, 0.0), glyph); + } + + // Move the coordinates + x += 1; + if x > MAPWIDTH - 1 { + x = 0; + y += 1; + } + } +} diff --git a/src/map_indexing_system.rs b/src/map_indexing_system.rs new file mode 100644 index 0000000..f49b28c --- /dev/null +++ b/src/map_indexing_system.rs @@ -0,0 +1,26 @@ +use super::{BlocksTile, Map, Position}; +use specs::prelude::*; + +pub struct MapIndexingSystem {} + +impl<'a> System<'a> for MapIndexingSystem { + type SystemData = (WriteExpect<'a, Map>, ReadStorage<'a, Position>, ReadStorage<'a, BlocksTile>, Entities<'a>); + + fn run(&mut self, data: Self::SystemData) { + let (mut map, position, blockers, entities) = data; + + map.populate_blocked(); + map.clear_content_index(); + for (entity, position) in (&entities, &position).join() { + let idx = map.xy_idx(position.x, position.y); + + let _p: Option<&BlocksTile> = blockers.get(entity); + if let Some(_p) = _p { + map.blocked[idx] = true; + } + + // Push the entity to the appropriate index slot. + map.tile_content[idx].push(entity); + } + } +} diff --git a/src/melee_combat_system.rs b/src/melee_combat_system.rs new file mode 100644 index 0000000..6b8aa87 --- /dev/null +++ b/src/melee_combat_system.rs @@ -0,0 +1,41 @@ +use super::{gamelog::GameLog, CombatStats, Name, SufferDamage, WantsToMelee}; +use specs::prelude::*; + +pub struct MeleeCombatSystem {} + +impl<'a> System<'a> for MeleeCombatSystem { + type SystemData = ( + Entities<'a>, + WriteExpect<'a, GameLog>, + WriteStorage<'a, WantsToMelee>, + ReadStorage<'a, Name>, + ReadStorage<'a, CombatStats>, + WriteStorage<'a, SufferDamage>, + ); + + fn run(&mut self, data: Self::SystemData) { + let (entities, mut log, mut wants_melee, names, combat_stats, mut inflict_damage) = data; + + for (_entity, wants_melee, name, stats) in (&entities, &wants_melee, &names, &combat_stats).join() { + if stats.hp <= 0 { + break; + } + let target_stats = combat_stats.get(wants_melee.target).unwrap(); + if target_stats.hp <= 0 { + break; + } + + let target_name = names.get(wants_melee.target).unwrap(); + let damage = i32::max(0, stats.power - target_stats.defence); + + if damage == 0 { + log.entries.push(format!("{} is unable to hurt {}.", &name.name, &target_name.name)); + } else { + log.entries.push(format!("{} hits {} for {} damage.", &name.name, &target_name.name, damage)); + SufferDamage::new_damage(&mut inflict_damage, wants_melee.target, damage); + } + } + + wants_melee.clear(); + } +} diff --git a/src/monster_ai_system.rs b/src/monster_ai_system.rs new file mode 100644 index 0000000..0d90ea8 --- /dev/null +++ b/src/monster_ai_system.rs @@ -0,0 +1,62 @@ +use super::{Map, Monster, Position, RunState, Viewshed, WantsToMelee}; +use rltk::Point; +use specs::prelude::*; + +pub struct MonsterAI {} + +impl<'a> System<'a> for MonsterAI { + #[allow(clippy::type_complexity)] + type SystemData = ( + WriteExpect<'a, Map>, + ReadExpect<'a, Point>, + ReadExpect<'a, Entity>, + ReadExpect<'a, RunState>, + Entities<'a>, + WriteStorage<'a, Viewshed>, + ReadStorage<'a, Monster>, + WriteStorage<'a, Position>, + WriteStorage<'a, WantsToMelee>, + ); + + fn run(&mut self, data: Self::SystemData) { + let ( + mut map, + player_pos, + player_entity, + runstate, + entities, + mut viewshed, + monster, + mut position, + mut wants_to_melee, + ) = data; + + if *runstate != RunState::MonsterTurn { + return; + } + + for (entity, mut viewshed, _monster, mut pos) in (&entities, &mut viewshed, &monster, &mut position).join() { + let distance = rltk::DistanceAlg::Pythagoras.distance2d(Point::new(pos.x, pos.y), *player_pos); + if distance < 1.5 { + wants_to_melee + .insert(entity, WantsToMelee { target: *player_entity }) + .expect("Unable to insert attack."); + } else if viewshed.visible_tiles.contains(&*player_pos) { + let path = rltk::a_star_search( + map.xy_idx(pos.x, pos.y) as i32, + map.xy_idx(player_pos.x, player_pos.y) as i32, + &mut *map, + ); + if path.success && path.steps.len() > 1 { + let mut idx = map.xy_idx(pos.x, pos.y); + map.blocked[idx] = false; + pos.x = (path.steps[1] as i32) % map.width; + pos.y = (path.steps[1] as i32) / map.width; + idx = map.xy_idx(pos.x, pos.y); + map.blocked[idx] = true; + viewshed.dirty = true; + } + } + } + } +} diff --git a/src/player.rs b/src/player.rs new file mode 100644 index 0000000..a2a8b73 --- /dev/null +++ b/src/player.rs @@ -0,0 +1,76 @@ +use super::{CombatStats, Map, Player, Position, RunState, State, Viewshed, WantsToMelee, MAPHEIGHT, MAPWIDTH}; +use rltk::{Point, Rltk, VirtualKeyCode}; +use specs::prelude::*; +use std::cmp::{max, min}; + +pub fn try_move_player(delta_x: i32, delta_y: i32, ecs: &mut World) { + let mut positions = ecs.write_storage::(); + let mut players = ecs.write_storage::(); + let mut viewsheds = ecs.write_storage::(); + let combat_stats = ecs.read_storage::(); + let map = ecs.fetch::(); + + let entities = ecs.entities(); + let mut wants_to_melee = ecs.write_storage::(); + + for (entity, _player, pos, viewshed) in (&entities, &mut players, &mut positions, &mut viewsheds).join() { + if pos.x + delta_x < 1 + || pos.x + delta_x > map.width - 1 + || pos.y + delta_y < 1 + || pos.y + delta_y > map.height - 1 + { + return; + } + let destination_idx = map.xy_idx(pos.x + delta_x, pos.y + delta_y); + + for potential_target in map.tile_content[destination_idx].iter() { + let target = combat_stats.get(*potential_target); + if let Some(_target) = target { + wants_to_melee.insert(entity, WantsToMelee { target: *potential_target }).expect("Add target failed."); + return; + } + } + + if !map.blocked[destination_idx] { + pos.x = min((MAPWIDTH as i32) - 1, max(0, pos.x + delta_x)); + pos.y = min((MAPHEIGHT as i32) - 1, max(0, pos.y + delta_y)); + viewshed.dirty = true; + let mut ppos = ecs.write_resource::(); + ppos.x = pos.x; + ppos.y = pos.y; + } + } +} + +pub fn player_input(gs: &mut State, ctx: &mut Rltk) -> RunState { + // Player movement + match ctx.key { + None => { + return RunState::AwaitingInput; + } + Some(key) => match key { + // Cardinals + VirtualKeyCode::Left | VirtualKeyCode::Numpad4 | VirtualKeyCode::H => { + try_move_player(-1, 0, &mut gs.ecs); + } + VirtualKeyCode::Right | VirtualKeyCode::Numpad6 | VirtualKeyCode::L => { + try_move_player(1, 0, &mut gs.ecs); + } + VirtualKeyCode::Up | VirtualKeyCode::Numpad8 | VirtualKeyCode::K => { + try_move_player(0, -1, &mut gs.ecs); + } + VirtualKeyCode::Down | VirtualKeyCode::Numpad2 | VirtualKeyCode::J => { + try_move_player(0, 1, &mut gs.ecs); + } + // Diagonals + VirtualKeyCode::Numpad9 | VirtualKeyCode::Y => try_move_player(1, -1, &mut gs.ecs), + VirtualKeyCode::Numpad7 | VirtualKeyCode::U => try_move_player(-1, -1, &mut gs.ecs), + VirtualKeyCode::Numpad3 | VirtualKeyCode::N => try_move_player(1, 1, &mut gs.ecs), + VirtualKeyCode::Numpad1 | VirtualKeyCode::B => try_move_player(-1, 1, &mut gs.ecs), + _ => { + return RunState::PlayerTurn; + } + }, + } + RunState::PlayerTurn +} diff --git a/src/rect.rs b/src/rect.rs new file mode 100644 index 0000000..6109287 --- /dev/null +++ b/src/rect.rs @@ -0,0 +1,21 @@ +pub struct Rect { + pub x1: i32, + pub x2: i32, + pub y1: i32, + pub y2: i32, +} + +impl Rect { + pub fn new(x: i32, y: i32, w: i32, h: i32) -> Rect { + Rect { x1: x, y1: y, x2: x + w, y2: y + h } + } + + //Returns true if this overlaps with other + pub fn intersect(&self, other: &Rect) -> bool { + self.x1 <= other.x2 && self.x2 >= other.x1 && self.y1 <= other.y2 && self.y2 >= other.y1 + } + + pub fn centre(&self) -> (i32, i32) { + ((self.x1 + self.x2) / 2, (self.y1 + self.y2) / 2) + } +} diff --git a/src/visibility_system.rs b/src/visibility_system.rs new file mode 100644 index 0000000..55da530 --- /dev/null +++ b/src/visibility_system.rs @@ -0,0 +1,41 @@ +use super::{Map, Player, Position, Viewshed}; +use rltk::{field_of_view, Point}; +use specs::prelude::*; + +pub struct VisibilitySystem {} + +impl<'a> System<'a> for VisibilitySystem { + type SystemData = ( + WriteExpect<'a, Map>, + Entities<'a>, + WriteStorage<'a, Viewshed>, + WriteStorage<'a, Position>, + ReadStorage<'a, Player>, + ); + + fn run(&mut self, data: Self::SystemData) { + let (mut map, entities, mut viewshed, pos, player) = data; + + for (ent, viewshed, pos) in (&entities, &mut viewshed, &pos).join() { + if viewshed.dirty { + viewshed.dirty = false; + viewshed.visible_tiles.clear(); + viewshed.visible_tiles = field_of_view(Point::new(pos.x, pos.y), viewshed.range, &*map); + viewshed.visible_tiles.retain(|p| p.x >= 0 && p.x < map.width && p.y >= 0 && p.y < map.height); + + // If this is the player, reveal what they can see + let _p: Option<&Player> = player.get(ent); + if let Some(_p) = _p { + for t in map.visible_tiles.iter_mut() { + *t = false; + } + for vis in viewshed.visible_tiles.iter() { + let idx = map.xy_idx(vis.x, vis.y); + map.revealed_tiles[idx] = true; + map.visible_tiles[idx] = true; + } + } + } + } + } +}