aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Pipfile2
-rw-r--r--Pipfile.lock180
-rw-r--r--ingame/src/main/kotlin/moe/nea89/sbdata/SBData.kt2
-rw-r--r--ingame/src/main/kotlin/moe/nea89/sbdata/dungeon/DungeonMapCoordinates.kt29
-rw-r--r--ingame/src/main/kotlin/moe/nea89/sbdata/souls/SoulESP.kt122
-rw-r--r--ingame/src/main/kotlin/moe/nea89/sbdata/utils/base64.kt8
-rw-r--r--sbdata/task.py3
-rw-r--r--sbdata/tasks/__init__.py2
-rw-r--r--sbdata/tasks/calculate_mapping_function.py31
-rw-r--r--sbdata/tasks/fetch_dungeon_loot.py (renamed from sbdata/tasks.py)1
10 files changed, 348 insertions, 32 deletions
diff --git a/Pipfile b/Pipfile
index 43c3bd6..e595392 100644
--- a/Pipfile
+++ b/Pipfile
@@ -9,6 +9,8 @@ mwparserfromhell = "*"
click = "*"
questionary = "*"
rich = "*"
+numpy = "*"
+sklearn = "*"
[dev-packages]
mypy = "*"
diff --git a/Pipfile.lock b/Pipfile.lock
index 33c0b7a..0157c7f 100644
--- a/Pipfile.lock
+++ b/Pipfile.lock
@@ -1,7 +1,7 @@
{
"_meta": {
"hash": {
- "sha256": "d800669875d1b92f0d8196a0fe4a8dd6302fdbc9bd9ddde374263bcd15e76aec"
+ "sha256": "c58b1ef7a832512e8dac14fc5a8d145b1abd5462db9b4bd2553518e7b4a57550"
},
"pipfile-spec": 6,
"requires": {
@@ -54,6 +54,14 @@
"markers": "python_version >= '3'",
"version": "==3.3"
},
+ "joblib": {
+ "hashes": [
+ "sha256:4158fcecd13733f8be669be0683b96ebdbbd38d23559f54dca7205aea1bf1e35",
+ "sha256:f21f109b3c7ff9d95f8387f752d0d9c34a02aa2f7060c2135f465da0e5160ff6"
+ ],
+ "markers": "python_version >= '3.6'",
+ "version": "==1.1.0"
+ },
"mwparserfromhell": {
"hashes": [
"sha256:0519497b8a7472298324ef92e1e82c1ab5cab85b4d64462d7ae46c4464c8b872",
@@ -88,6 +96,32 @@
"index": "pypi",
"version": "==0.6.4"
},
+ "numpy": {
+ "hashes": [
+ "sha256:07a8c89a04997625236c5ecb7afe35a02af3896c8aa01890a849913a2309c676",
+ "sha256:08d9b008d0156c70dc392bb3ab3abb6e7a711383c3247b410b39962263576cd4",
+ "sha256:201b4d0552831f7250a08d3b38de0d989d6f6e4658b709a02a73c524ccc6ffce",
+ "sha256:2c10a93606e0b4b95c9b04b77dc349b398fdfbda382d2a39ba5a822f669a0123",
+ "sha256:3ca688e1b9b95d80250bca34b11a05e389b1420d00e87a0d12dc45f131f704a1",
+ "sha256:48a3aecd3b997bf452a2dedb11f4e79bc5bfd21a1d4cc760e703c31d57c84b3e",
+ "sha256:568dfd16224abddafb1cbcce2ff14f522abe037268514dd7e42c6776a1c3f8e5",
+ "sha256:5bfb1bb598e8229c2d5d48db1860bcf4311337864ea3efdbe1171fb0c5da515d",
+ "sha256:639b54cdf6aa4f82fe37ebf70401bbb74b8508fddcf4797f9fe59615b8c5813a",
+ "sha256:8251ed96f38b47b4295b1ae51631de7ffa8260b5b087808ef09a39a9d66c97ab",
+ "sha256:92bfa69cfbdf7dfc3040978ad09a48091143cffb778ec3b03fa170c494118d75",
+ "sha256:97098b95aa4e418529099c26558eeb8486e66bd1e53a6b606d684d0c3616b168",
+ "sha256:a3bae1a2ed00e90b3ba5f7bd0a7c7999b55d609e0c54ceb2b076a25e345fa9f4",
+ "sha256:c34ea7e9d13a70bf2ab64a2532fe149a9aced424cd05a2c4ba662fd989e3e45f",
+ "sha256:dbc7601a3b7472d559dc7b933b18b4b66f9aa7452c120e87dfb33d02008c8a18",
+ "sha256:e7927a589df200c5e23c57970bafbd0cd322459aa7b1ff73b7c2e84d6e3eae62",
+ "sha256:f8c1f39caad2c896bc0018f699882b345b2a63708008be29b1f355ebf6f933fe",
+ "sha256:f950f8845b480cffe522913d35567e29dd381b0dc7e4ce6a4a9f9156417d2430",
+ "sha256:fade0d4f4d292b6f39951b6836d7a3c7ef5b2347f3c420cd9820a1d90d794802",
+ "sha256:fdf3c08bce27132395d3c3ba1503cac12e17282358cb4bddc25cc46b0aca07aa"
+ ],
+ "index": "pypi",
+ "version": "==1.22.3"
+ },
"prompt-toolkit": {
"hashes": [
"sha256:30129d870dcb0b3b6a53efdc9d0a83ea96162ffd28ffe077e94215b233dc670c",
@@ -122,19 +156,101 @@
},
"rich": {
"hashes": [
- "sha256:14bfd0507edc633e021b02c45cbf7ca22e33b513817627b8de3412f047a3e798",
- "sha256:fdcd2f8d416e152bcf35c659987038d1ae5a7bd336e821ca7551858a4c7e38a9"
+ "sha256:3fba9dd15ebe048e2795a02ac19baee79dc12cc50b074ef70f2958cd651b59a9",
+ "sha256:ce5c714e984a2d185399e4e1dd1f8b2feacb7cecfc576f1522425643a36a57ea"
],
"index": "pypi",
- "version": "==12.0.0"
+ "version": "==12.0.1"
+ },
+ "scikit-learn": {
+ "hashes": [
+ "sha256:08ef968f6b72033c16c479c966bf37ccd49b06ea91b765e1cc27afefe723920b",
+ "sha256:158faf30684c92a78e12da19c73feff9641a928a8024b4fa5ec11d583f3d8a87",
+ "sha256:16455ace947d8d9e5391435c2977178d0ff03a261571e67f627c8fee0f9d431a",
+ "sha256:245c9b5a67445f6f044411e16a93a554edc1efdcce94d3fc0bc6a4b9ac30b752",
+ "sha256:285db0352e635b9e3392b0b426bc48c3b485512d3b4ac3c7a44ec2a2ba061e66",
+ "sha256:2f3b453e0b149898577e301d27e098dfe1a36943f7bb0ad704d1e548efc3b448",
+ "sha256:46f431ec59dead665e1370314dbebc99ead05e1c0a9df42f22d6a0e00044820f",
+ "sha256:55f2f3a8414e14fbee03782f9fe16cca0f141d639d2b1c1a36779fa069e1db57",
+ "sha256:5cb33fe1dc6f73dc19e67b264dbb5dde2a0539b986435fdd78ed978c14654830",
+ "sha256:75307d9ea39236cad7eea87143155eea24d48f93f3a2f9389c817f7019f00705",
+ "sha256:7626a34eabbf370a638f32d1a3ad50526844ba58d63e3ab81ba91e2a7c6d037e",
+ "sha256:7a93c1292799620df90348800d5ac06f3794c1316ca247525fa31169f6d25855",
+ "sha256:7d6b2475f1c23a698b48515217eb26b45a6598c7b1840ba23b3c5acece658dbb",
+ "sha256:80095a1e4b93bd33261ef03b9bc86d6db649f988ea4dbcf7110d0cded8d7213d",
+ "sha256:85260fb430b795d806251dd3bb05e6f48cdc777ac31f2bcf2bc8bbed3270a8f5",
+ "sha256:9369b030e155f8188743eb4893ac17a27f81d28a884af460870c7c072f114243",
+ "sha256:a053a6a527c87c5c4fa7bf1ab2556fa16d8345cf99b6c5a19030a4a7cd8fd2c0",
+ "sha256:a90b60048f9ffdd962d2ad2fb16367a87ac34d76e02550968719eb7b5716fd10",
+ "sha256:a999c9f02ff9570c783069f1074f06fe7386ec65b84c983db5aeb8144356a355",
+ "sha256:b1391d1a6e2268485a63c3073111fe3ba6ec5145fc957481cfd0652be571226d",
+ "sha256:b54a62c6e318ddbfa7d22c383466d38d2ee770ebdb5ddb668d56a099f6eaf75f",
+ "sha256:b5870959a5484b614f26d31ca4c17524b1b0317522199dc985c3b4256e030767",
+ "sha256:bc3744dabc56b50bec73624aeca02e0def06b03cb287de26836e730659c5d29c",
+ "sha256:d93d4c28370aea8a7cbf6015e8a669cd5d69f856cc2aa44e7a590fb805bb5583",
+ "sha256:d9aac97e57c196206179f674f09bc6bffcd0284e2ba95b7fe0b402ac3f986023",
+ "sha256:da3c84694ff693b5b3194d8752ccf935a665b8b5edc33a283122f4273ca3e687",
+ "sha256:e174242caecb11e4abf169342641778f68e1bfaba80cd18acd6bc84286b9a534",
+ "sha256:eabceab574f471de0b0eb3f2ecf2eee9f10b3106570481d007ed1c84ebf6d6a1",
+ "sha256:f14517e174bd7332f1cca2c959e704696a5e0ba246eb8763e6c24876d8710049",
+ "sha256:fa38a1b9b38ae1fad2863eff5e0d69608567453fdfc850c992e6e47eb764e846",
+ "sha256:ff3fa8ea0e09e38677762afc6e14cad77b5e125b0ea70c9bba1992f02c93b028",
+ "sha256:ff746a69ff2ef25f62b36338c615dd15954ddc3ab8e73530237dd73235e76d62"
+ ],
+ "markers": "python_version >= '3.7'",
+ "version": "==1.0.2"
+ },
+ "scipy": {
+ "hashes": [
+ "sha256:011d4386b53b933142f58a652aa0f149c9b9242abd4f900b9f4ea5fbafc86b89",
+ "sha256:16e09ef68b352d73befa8bcaf3ebe25d3941fe1a58c82909d5589856e6bc8174",
+ "sha256:31d4f2d6b724bc9a98e527b5849b8a7e589bf1ea630c33aa563eda912c9ff0bd",
+ "sha256:38aa39b6724cb65271e469013aeb6f2ce66fd44f093e241c28a9c6bc64fd79ed",
+ "sha256:3d573228c10a3a8c32b9037be982e6440e411b443a6267b067cac72f690b8d56",
+ "sha256:3d9dd6c8b93a22bf9a3a52d1327aca7e092b1299fb3afc4f89e8eba381be7b59",
+ "sha256:559a8a4c03a5ba9fe3232f39ed24f86457e4f3f6c0abbeae1fb945029f092720",
+ "sha256:5e73343c5e0d413c1f937302b2e04fb07872f5843041bcfd50699aef6e95e399",
+ "sha256:723b9f878095ed994756fa4ee3060c450e2db0139c5ba248ee3f9628bd64e735",
+ "sha256:87b01c7d5761e8a266a0fbdb9d88dcba0910d63c1c671bdb4d99d29f469e9e03",
+ "sha256:8f4d059a97b29c91afad46b1737274cb282357a305a80bdd9e8adf3b0ca6a3f0",
+ "sha256:92b2c2af4183ed09afb595709a8ef5783b2baf7f41e26ece24e1329c109691a7",
+ "sha256:937d28722f13302febde29847bbe554b89073fbb924a30475e5ed7b028898b5f",
+ "sha256:a279e27c7f4566ef18bab1b1e2c37d168e365080974758d107e7d237d3f0f484",
+ "sha256:ad5be4039147c808e64f99c0e8a9641eb5d2fa079ff5894dcd8240e94e347af4",
+ "sha256:ae3e327da323d82e918e593460e23babdce40d7ab21490ddf9fc06dec6b91a18",
+ "sha256:bb7088e89cd751acf66195d2f00cf009a1ea113f3019664032d9075b1e727b6c",
+ "sha256:c17a1878d00a5dd2797ccd73623ceca9d02375328f6218ee6d921e1325e61aff",
+ "sha256:c2bae431d127bf0b1da81fc24e4bba0a84d058e3a96b9dd6475dfcb3c5e8761e",
+ "sha256:de2e80ee1d925984c2504812a310841c241791c5279352be4707cdcd7c255039",
+ "sha256:e6f0cd9c0bd374ef834ee1e0f0999678d49dcc400ea6209113d81528958f97c7",
+ "sha256:f3720d0124aced49f6f2198a6900304411dbbeed12f56951d7c66ebef05e3df6",
+ "sha256:f4a6d3b9f9797eb2d43938ac2c5d96d02aed17ef170c8b38f11798717523ddba"
+ ],
+ "markers": "python_version < '3.11' and python_version >= '3.8'",
+ "version": "==1.8.0"
+ },
+ "sklearn": {
+ "hashes": [
+ "sha256:e23001573aa194b834122d2b9562459bf5ae494a2d59ca6b8aa22c85a44c0e31"
+ ],
+ "index": "pypi",
+ "version": "==0.0"
+ },
+ "threadpoolctl": {
+ "hashes": [
+ "sha256:8b99adda265feb6773280df41eece7b2e6561b772d21ffd52e372f999024907b",
+ "sha256:a335baacfaa4400ae1f0d8e3a58d6674d2f8828e3716bb2802c44955ad391380"
+ ],
+ "markers": "python_version >= '3.6'",
+ "version": "==3.1.0"
},
"urllib3": {
"hashes": [
- "sha256:000ca7f471a233c2251c6c7023ee85305721bfdf18621ebff4fd17a8653427ed",
- "sha256:0e7c33d9a63e7ddfcb86780aac87befc2fbddf46c58dbb487e0855f7ceec283c"
+ "sha256:44ece4d53fb1706f667c9bd1c648f5469a2ec925fcf3a776667042d645472c14",
+ "sha256:aabaf16477806a5e1dd19aa41f8c2b7950dd3c746362d7e3223dbe6de6ac448e"
],
- "markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4' and python_version < '4.0'",
- "version": "==1.26.8"
+ "markers": "python_version >= '2.7' and python_version not in '3.0, 3.1, 3.2, 3.3, 3.4' and python_full_version < '4.0.0'",
+ "version": "==1.26.9"
},
"wcwidth": {
"hashes": [
@@ -147,32 +263,32 @@
"develop": {
"mypy": {
"hashes": [
- "sha256:0b52778a018559a256c819ee31b2e21e10b31ddca8705624317253d6d08dbc35",
- "sha256:0fdc9191a49c77ab5fa0439915d405e80a1118b163ab03cd2a530f346b12566a",
- "sha256:13677cb8b050f03b5bb2e8bf7b2668cd918b001d56c2435082bbfc9d5f730f42",
- "sha256:1903c92ff8642d521b4627e51a67e49f5be5aedb1fb03465b3aae4c3338ec491",
- "sha256:1f66f2309cdbb07e95e60e83fb4a8272095bd4ea6ee58bf9a70d5fb304ec3e3f",
- "sha256:2dba92f58610d116f68ec1221fb2de2a346d081d17b24a784624389b17a4b3f9",
- "sha256:2efd76893fb8327eca7e942e21b373e6f3c5c083ff860fb1e82ddd0462d662bd",
- "sha256:3ac14949677ae9cb1adc498c423b194ad4d25b13322f6fe889fb72b664c79121",
- "sha256:471af97c35a32061883b0f8a3305ac17947fd42ce962ca9e2b0639eb9141492f",
- "sha256:51be997c1922e2b7be514a5215d1e1799a40832c0a0dee325ba8794f2c48818f",
- "sha256:628f5513268ebbc563750af672ccba5eef7f92d2d90154233edd498dfb98ca4e",
- "sha256:68038d514ae59d5b2f326be502a359160158d886bd153fc2489dbf7a03c44c96",
- "sha256:6eab2bcc2b9489b7df87d7c20743b66d13254ad4d6430e1dfe1a655d51f0933d",
- "sha256:712affcc456de637e774448c73e21c84dfa5a70bcda34e9b0be4fb898a9e8e07",
- "sha256:71bec3d2782d0b1fecef7b1c436253544d81c1c0e9ca58190aed9befd8f081c5",
- "sha256:83f66190e3c32603217105913fbfe0a3ef154ab6bbc7ef2c989f5b2957b55840",
- "sha256:8aaf18d0f8bc3ffba56d32a85971dfbd371a5be5036da41ac16aefec440eff17",
- "sha256:a0e5657ccaedeb5fdfda59918cc98fc6d8a8e83041bc0cec347a2ab6915f9998",
- "sha256:a168da06eccf51875fdff5f305a47f021f23f300e2b89768abdac24538b1f8ec",
- "sha256:b1a116c451b41e35afc09618f454b5c2704ba7a4e36f9ff65014fef26bb6075b",
- "sha256:b2fa5f2d597478ccfe1f274f8da2f50ea1e63da5a7ae2342c5b3b2f3e57ec340",
- "sha256:d9d7647505bf427bc7931e8baf6cacf9be97e78a397724511f20ddec2a850752",
- "sha256:f8fe1bfab792e4300f80013edaf9949b34e4c056a7b2531b5ef3a0fb9d598ae2"
+ "sha256:0e2dd88410937423fba18e57147dd07cd8381291b93d5b1984626f173a26543e",
+ "sha256:10daab80bc40f84e3f087d896cdb53dc811a9f04eae4b3f95779c26edee89d16",
+ "sha256:17e44649fec92e9f82102b48a3bf7b4a5510ad0cd22fa21a104826b5db4903e2",
+ "sha256:1a0459c333f00e6a11cbf6b468b870c2b99a906cb72d6eadf3d1d95d38c9352c",
+ "sha256:246e1aa127d5b78488a4a0594bd95f6d6fb9d63cf08a66dafbff8595d8891f67",
+ "sha256:2b184db8c618c43c3a31b32ff00cd28195d39e9c24e7c3b401f3db7f6e5767f5",
+ "sha256:2bc249409a7168d37c658e062e1ab5173300984a2dada2589638568ddc1db02b",
+ "sha256:3841b5433ff936bff2f4dc8d54cf2cdbfea5d8e88cedfac45c161368e5770ba6",
+ "sha256:4c3e497588afccfa4334a9986b56f703e75793133c4be3a02d06a3df16b67a58",
+ "sha256:5bf44840fb43ac4074636fd47ee476d73f0039f4f54e86d7265077dc199be24d",
+ "sha256:64235137edc16bee6f095aba73be5334677d6f6bdb7fa03cfab90164fa294a17",
+ "sha256:6776e5fa22381cc761df53e7496a805801c1a751b27b99a9ff2f0ca848c7eca0",
+ "sha256:6ce34a118d1a898f47def970a2042b8af6bdcc01546454726c7dd2171aa6dfca",
+ "sha256:6f6ad963172152e112b87cc7ec103ba0f2db2f1cd8997237827c052a3903eaa6",
+ "sha256:6f7106cbf9cc2f403693bf50ed7c9fa5bb3dfa9007b240db3c910929abe2a322",
+ "sha256:7742d2c4e46bb5017b51c810283a6a389296cda03df805a4f7869a6f41246534",
+ "sha256:9521c1265ccaaa1791d2c13582f06facf815f426cd8b07c3a485f486a8ffc1f3",
+ "sha256:a1b383fe99678d7402754fe90448d4037f9512ce70c21f8aee3b8bf48ffc51db",
+ "sha256:b840cfe89c4ab6386c40300689cd8645fc8d2d5f20101c7f8bd23d15fca14904",
+ "sha256:d8d3ba77e56b84cd47a8ee45b62c84b6d80d32383928fe2548c9a124ea0a725c",
+ "sha256:dcd955f36e0180258a96f880348fbca54ce092b40fbb4b37372ae3b25a0b0a46",
+ "sha256:e865fec858d75b78b4d63266c9aff770ecb6a39dfb6d6b56c47f7f8aba6baba8",
+ "sha256:edf7237137a1a9330046dbb14796963d734dd740a98d5e144a3eb1d267f5f9ee"
],
"index": "pypi",
- "version": "==0.940"
+ "version": "==0.942"
},
"mypy-extensions": {
"hashes": [
diff --git a/ingame/src/main/kotlin/moe/nea89/sbdata/SBData.kt b/ingame/src/main/kotlin/moe/nea89/sbdata/SBData.kt
index 979e26d..fd839d6 100644
--- a/ingame/src/main/kotlin/moe/nea89/sbdata/SBData.kt
+++ b/ingame/src/main/kotlin/moe/nea89/sbdata/SBData.kt
@@ -1,6 +1,7 @@
package moe.nea89.sbdata
import moe.nea89.sbdata.dungeon.DungeonMapCoordinates
+import moe.nea89.sbdata.souls.SoulESP
import net.minecraftforge.client.ClientCommandHandler
import net.minecraftforge.common.MinecraftForge
import net.minecraftforge.fml.common.Mod
@@ -34,6 +35,7 @@ class SBData {
@Mod.EventHandler
fun init(event: FMLInitializationEvent) {
MinecraftForge.EVENT_BUS.register(DungeonMapCoordinates)
+ MinecraftForge.EVENT_BUS.register(SoulESP)
}
@Mod.EventHandler
diff --git a/ingame/src/main/kotlin/moe/nea89/sbdata/dungeon/DungeonMapCoordinates.kt b/ingame/src/main/kotlin/moe/nea89/sbdata/dungeon/DungeonMapCoordinates.kt
index 02df59c..4fe9a8a 100644
--- a/ingame/src/main/kotlin/moe/nea89/sbdata/dungeon/DungeonMapCoordinates.kt
+++ b/ingame/src/main/kotlin/moe/nea89/sbdata/dungeon/DungeonMapCoordinates.kt
@@ -14,6 +14,8 @@ import java.awt.datatransfer.StringSelection
object DungeonMapCoordinates {
+ var logMarkers = false
+
init {
Commands.addSubCommand("map") {
when (args.firstOrNull()) {
@@ -34,6 +36,25 @@ object DungeonMapCoordinates {
}
}
}
+ "logmarkers" -> {
+ if (args.size == 2) {
+ when (args[1]) {
+ "on" -> {
+ logMarkers = true
+ reply("Turned on marker order logging")
+ }
+ "off" -> {
+ logMarkers = false
+ reply("Turned off marker order logging")
+ }
+ else -> {
+ reply("logmarkers <on/off>")
+ }
+ }
+ } else {
+ reply("Marker order logging is ${if (logMarkers) "on" else "off"}.")
+ }
+ }
"load" -> {
val base = SBData.configDirectory.resolve("mapdata")
base.mkdirs()
@@ -89,8 +110,16 @@ object DungeonMapCoordinates {
.firstNotNullOfOrNull { FLOOR_REGEX.find(it) }
?.let { it.groupValues[1] } ?: return
logPosition(player, playerMarker, floor)
+ if (logMarkers) {
+ println("-----------")
+ mapData.mapDecorations.entries.sortedBy { it.key }.forEach { (key, value) ->
+ println(" $key -> ${value.func_176112_b().toInt() / 2 + 64} ${value.func_176113_c().toInt() / 2 + 64}")
+ }
+ println("-----------")
+ }
}
+
fun logPosition(player: EntityPlayerSP, playerMarker: Vec4b, floor: String) {
val coordList = coords.computeIfAbsent(floor) { hashSetOf() }
val coordEntry = Coordinates(
diff --git a/ingame/src/main/kotlin/moe/nea89/sbdata/souls/SoulESP.kt b/ingame/src/main/kotlin/moe/nea89/sbdata/souls/SoulESP.kt
new file mode 100644
index 0000000..dd7cad8
--- /dev/null
+++ b/ingame/src/main/kotlin/moe/nea89/sbdata/souls/SoulESP.kt
@@ -0,0 +1,122 @@
+package moe.nea89.sbdata.souls
+
+import com.google.gson.Gson
+import com.google.gson.JsonObject
+import moe.nea89.sbdata.Commands
+import moe.nea89.sbdata.utils.base64decode
+import moe.nea89.sbdata.utils.interpolate
+import net.minecraft.client.Minecraft
+import net.minecraft.client.renderer.GlStateManager
+import net.minecraft.client.renderer.Tessellator
+import net.minecraft.client.renderer.vertex.DefaultVertexFormats
+import net.minecraft.entity.item.EntityArmorStand
+import net.minecraft.init.Items
+import net.minecraft.util.BlockPos
+import net.minecraft.util.EnumFacing
+import net.minecraft.util.Vec3
+import net.minecraftforge.client.event.RenderWorldLastEvent
+import net.minecraftforge.event.world.WorldEvent
+import net.minecraftforge.fml.common.eventhandler.SubscribeEvent
+import net.minecraftforge.fml.common.gameevent.TickEvent
+import org.lwjgl.opengl.GL11
+
+object SoulESP {
+ var showESP = false
+
+ init {
+ Commands.addSubCommand("soulesp") {
+ when (args.firstOrNull()) {
+ "on" -> {
+ showESP = true
+ reply("Turned soul ESP on.")
+ }
+ "off" -> {
+ showESP = false
+ reply("Turned soul ESP off.")
+ }
+ null -> {
+ reply("Use /soulesp <on/off/size <range>>")
+ }
+ }
+ }
+ }
+
+ val soulLocations = mutableSetOf<BlockPos>()
+
+ @SubscribeEvent
+ fun onWorldChange(ev: WorldEvent.Load) {
+ soulLocations.clear()
+ }
+
+ val fairySoulTexture =
+ "http://textures.minecraft.net/texture/b96923ad247310007f6ae5d326d847ad53864cf16c3565a181dc8e6b20be2387"
+
+ @SubscribeEvent
+ fun onTick(ev: TickEvent.PlayerTickEvent) {
+ if (ev.phase != TickEvent.Phase.END) return
+ if (!showESP) return
+
+ val player = ev.player
+ player.worldObj.getEntities(EntityArmorStand::class.java) {
+ if (it == null) return@getEntities false
+ val helm = it.getEquipmentInSlot(4)
+ if (helm == null || helm.item != Items.skull) return@getEntities false
+ val skindata = helm
+ .getSubCompound("SkullOwner", true)
+ .getCompoundTag("Properties")
+ .getTagList("textures", 10)
+ .getCompoundTagAt(0)
+ .getString("Value")
+ .base64decode()
+ if (skindata.isEmpty()) return@getEntities false
+ try {
+ val skinJson = Gson().fromJson(skindata.decodeToString(), JsonObject::class.java)
+ return@getEntities skinJson.getAsJsonObject("textures").getAsJsonObject("SKIN").get("url").asString == fairySoulTexture
+ } catch (ex: Exception) {
+ }
+ return@getEntities false
+ }.map {
+ soulLocations.add(it.position.offset(EnumFacing.UP, 1))
+ }
+ }
+
+ @SubscribeEvent
+ fun onRender(ev: RenderWorldLastEvent) {
+ if (!showESP) return
+ val thePlayer = Minecraft.getMinecraft().renderViewEntity
+ GlStateManager.disableCull()
+ GlStateManager.disableDepth()
+ GlStateManager.disableTexture2D()
+ val tesselator = Tessellator.getInstance()
+ val worldrenderer = tesselator.worldRenderer
+ GlStateManager.color(1.0F, 0.0F, 1.0F, 1.0F)
+ soulLocations.forEach { soul ->
+ val part = ev.partialTicks.toDouble()
+ val x = soul.x - part.interpolate(thePlayer.lastTickPosX, thePlayer.posX)
+ val y = soul.y - part.interpolate(thePlayer.lastTickPosY, thePlayer.posY)
+ val z = soul.z - part.interpolate(thePlayer.lastTickPosZ, thePlayer.posZ)
+
+ worldrenderer.begin(GL11.GL_TRIANGLE_STRIP, DefaultVertexFormats.POSITION)
+ worldrenderer.pos(x + 1, y + 1, z).endVertex()
+ worldrenderer.pos(x, y + 1, z).endVertex()
+ worldrenderer.pos(x + 1, y, z).endVertex()
+ worldrenderer.pos(x, y, z).endVertex()
+ worldrenderer.pos(x, y, z + 1).endVertex()
+ worldrenderer.pos(x, y + 1, z).endVertex()
+ worldrenderer.pos(x, y + 1, z + 1).endVertex()
+ worldrenderer.pos(x + 1, y + 1, z).endVertex()
+ worldrenderer.pos(x + 1, y + 1, z + 1).endVertex()
+ worldrenderer.pos(x + 1, y, z).endVertex()
+ worldrenderer.pos(x + 1, y, z + 1).endVertex()
+ worldrenderer.pos(x, y, z + 1).endVertex()
+ worldrenderer.pos(x + 1, y + 1, z + 1).endVertex()
+ worldrenderer.pos(x, y + 1, z + 1).endVertex()
+ tesselator.draw()
+ }
+ GlStateManager.enableCull()
+ GlStateManager.enableDepth()
+ GlStateManager.enableTexture2D()
+
+ }
+
+}
diff --git a/ingame/src/main/kotlin/moe/nea89/sbdata/utils/base64.kt b/ingame/src/main/kotlin/moe/nea89/sbdata/utils/base64.kt
new file mode 100644
index 0000000..4e95335
--- /dev/null
+++ b/ingame/src/main/kotlin/moe/nea89/sbdata/utils/base64.kt
@@ -0,0 +1,8 @@
+package moe.nea89.sbdata.utils
+
+import java.util.*
+
+
+fun String.base64decode() = Base64.getDecoder().decode(this)
+
+fun Double.interpolate(left: Double, right: Double): Double = left * (1 - this) + right * this
diff --git a/sbdata/task.py b/sbdata/task.py
index 7011ca2..90f23e6 100644
--- a/sbdata/task.py
+++ b/sbdata/task.py
@@ -40,6 +40,9 @@ class Arguments:
return question.ask()
return value
+ def get_arg(self, label: str, arg_name: str, mapper: typing.Callable[[str], _T]) -> _T:
+ return mapper(self.get_value(label, self.args.get(arg_name), questionary.text('Missing ' + label)))
+
def has_flag(self, param: str) -> bool:
return param in self.flags
diff --git a/sbdata/tasks/__init__.py b/sbdata/tasks/__init__.py
new file mode 100644
index 0000000..737c65c
--- /dev/null
+++ b/sbdata/tasks/__init__.py
@@ -0,0 +1,2 @@
+from .fetch_dungeon_loot import fetch_dungeon_loot
+from .calculate_mapping_function import calculate_mapping_function
diff --git a/sbdata/tasks/calculate_mapping_function.py b/sbdata/tasks/calculate_mapping_function.py
new file mode 100644
index 0000000..37185a8
--- /dev/null
+++ b/sbdata/tasks/calculate_mapping_function.py
@@ -0,0 +1,31 @@
+import pathlib
+import random
+import numpy as np
+from sklearn.linear_model import LinearRegression
+
+from sbdata.task import register_task, Arguments
+
+
+@register_task("Calculate Map Coordinate Function")
+def calculate_mapping_function(args: Arguments):
+ csv = args.get_arg("Coordinate CSV", "coords", pathlib.Path)
+ points = [[int(x) for x in y.split(",")] for y in csv.read_text().splitlines()[1:]]
+ xs = [(a[0], a[2]) for a in points]
+ zs = [(a[1], a[3]) for a in points]
+ random.shuffle(xs)
+ random.shuffle(zs)
+ find_best_function_for("X", xs)
+ find_best_function_for("Z", zs)
+
+
+def find_best_function_for(label: str, l: list[tuple[int, int]]):
+ x = np.array([a[0] for a in l]).reshape((-1, 1))
+ y = np.array([a[1] for a in l])
+ model = LinearRegression()
+ model.fit(x, y)
+ print(f'------------')
+ print(f' {label} Coordinate:')
+ print(f" Score: {model.score(x, y)}")
+ print(f" Slope: {model.coef_[0]}")
+ print(f" Intercept: {model.intercept_}")
+ print(f'------------')
diff --git a/sbdata/tasks.py b/sbdata/tasks/fetch_dungeon_loot.py
index f50b530..bf7ef64 100644
--- a/sbdata/tasks.py
+++ b/sbdata/tasks/fetch_dungeon_loot.py
@@ -71,3 +71,4 @@ def fetch_dungeon_loot(args: Arguments):
cost = defaults[min(f for f in defaults.keys() if f >= ifloor)]
items.append(DungeonDrop(item, ifloor, chest, cost, drop_chances))
return items
+