mirror of
https://github.com/VolmitSoftware/Iris.git
synced 2025-12-19 23:19:21 +00:00
Compare commits
315 Commits
old/iris3
...
2.7.7-1.20
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
99d3dba440 | ||
|
|
5a44e79ad1 | ||
|
|
86808017db | ||
|
|
f735db9843 | ||
|
|
5a333c23ac | ||
|
|
4d2d51edfa | ||
|
|
dcfd5a0cd8 | ||
|
|
a821c0da50 | ||
|
|
804147e2c4 | ||
|
|
ed346291f9 | ||
|
|
2190f6eff8 | ||
|
|
ce30e24e42 | ||
|
|
d5e13541c8 | ||
|
|
2e707adaa0 | ||
|
|
4d8e36cb05 | ||
|
|
73b710cdde | ||
|
|
09182bf3f3 | ||
|
|
9a945837cd | ||
|
|
b64c821ef4 | ||
|
|
a9ab3bc519 | ||
|
|
94292cea6e | ||
|
|
b5fdeb2a02 | ||
|
|
fa3ac36e8c | ||
|
|
6632d1b65f | ||
|
|
8805693800 | ||
|
|
93db7ee0ee | ||
|
|
9ba4dd4099 | ||
|
|
36efacf43c | ||
|
|
d9bf91afa5 | ||
|
|
b0c96be841 | ||
|
|
673b08f174 | ||
|
|
989778af26 | ||
|
|
f5a3a7eb1a | ||
|
|
7a97928c21 | ||
|
|
12a6d022cf | ||
|
|
e3d2dfa99e | ||
|
|
35cc39e9e2 | ||
|
|
006b0b4a03 | ||
|
|
ec939b9f78 | ||
|
|
7a94f53735 | ||
|
|
a9efe146ba | ||
|
|
956e2f6b06 | ||
|
|
72623e0acf | ||
|
|
e0f673bc3c | ||
|
|
fe40f12d2e | ||
|
|
0fda7a8506 | ||
|
|
22887da769 | ||
|
|
a1e0a8ffc1 | ||
|
|
62010116d7 | ||
|
|
6ebcd02ae6 | ||
|
|
051015656a | ||
|
|
ee082762c6 | ||
|
|
e967b5e052 | ||
|
|
36505e2fa1 | ||
|
|
502aa054f6 | ||
|
|
cc5a880fd7 | ||
|
|
6f9ad8b0eb | ||
|
|
ac6ab74d48 | ||
|
|
807ed2b247 | ||
|
|
367de5a8fd | ||
|
|
5bf2da714a | ||
|
|
cc90f42deb | ||
|
|
20ceaead09 | ||
|
|
3ec2f8fb7b | ||
|
|
6c5fac154e | ||
|
|
540ab8f0d2 | ||
|
|
17d2ac8d70 | ||
|
|
a6ebdead19 | ||
|
|
aa7631ecd0 | ||
|
|
4e138cad9f | ||
|
|
7e55b5fcee | ||
|
|
e19e5278b4 | ||
|
|
dfcd2dc83e | ||
|
|
8775f842e6 | ||
|
|
7b07a4ba6c | ||
|
|
d78e5973e9 | ||
|
|
110d296184 | ||
|
|
23cd5c117b | ||
|
|
131c4692bc | ||
|
|
f6571367db | ||
|
|
f5c64c7480 | ||
|
|
085f63a915 | ||
|
|
3e022e1931 | ||
|
|
0dba3725ae | ||
|
|
8bb409df4e | ||
|
|
603168a147 | ||
|
|
2a95edd860 | ||
|
|
e94406fb45 | ||
|
|
e5a7b5d0c6 | ||
|
|
d6f816fe2f | ||
|
|
c15d4a349f | ||
|
|
3ce832583c | ||
|
|
5514fd2645 | ||
|
|
66d07dcaca | ||
|
|
c1cf8e88ee | ||
|
|
684bd739b9 | ||
|
|
d4c0e07b1d | ||
|
|
a6ea6fcfb2 | ||
|
|
c366ec0c40 | ||
|
|
8d715e2e4e | ||
|
|
dea3ec80ac | ||
|
|
4053f05ba9 | ||
|
|
ef07ec2c62 | ||
|
|
0ffc64231b | ||
|
|
fe112c3ba5 | ||
|
|
2fa03aac3b | ||
|
|
6ac5ad880d | ||
|
|
54f14392d9 | ||
|
|
c7ecdaf8a8 | ||
|
|
497c24a3b6 | ||
|
|
00aa26e602 | ||
|
|
3796381156 | ||
|
|
b0c5700cf5 | ||
|
|
78a4b1d2ce | ||
|
|
e5e6b9848f | ||
|
|
3e36f57f14 | ||
|
|
d794ede4d8 | ||
|
|
7a4d97d76a | ||
|
|
e76ab1d367 | ||
|
|
9731feff7f | ||
|
|
4ce790082d | ||
|
|
065b748036 | ||
|
|
76891d246f | ||
|
|
0832007991 | ||
|
|
87302a046c | ||
|
|
f0f7453b32 | ||
|
|
2991bea248 | ||
|
|
673b42c2f5 | ||
|
|
7d994e27e3 | ||
|
|
5f2b82aac7 | ||
|
|
af1a03cb67 | ||
|
|
85fbbeca9d | ||
|
|
a64272620f | ||
|
|
ef9966d02b | ||
|
|
a28e5bb38a | ||
|
|
34670759e9 | ||
|
|
7dd1d3881a | ||
|
|
7b93542014 | ||
|
|
ea1ac0a154 | ||
|
|
35c7068fa6 | ||
|
|
db4cbb2ea6 | ||
|
|
fa7c073999 | ||
|
|
72a077662d | ||
|
|
137abb04b2 | ||
|
|
211b15332d | ||
|
|
f6fbcade17 | ||
|
|
1ef115fee8 | ||
|
|
7973444fc5 | ||
|
|
2bdb0bfa69 | ||
|
|
bfb6f82ea3 | ||
|
|
7729ce3753 | ||
|
|
f6ea171669 | ||
|
|
ff081ebc11 | ||
|
|
0818f971fe | ||
|
|
27070f44c7 | ||
|
|
8331cbe375 | ||
|
|
f533ec34b0 | ||
|
|
23d4fcb827 | ||
|
|
a248962f1b | ||
|
|
afa8fad8e9 | ||
|
|
4c423bb493 | ||
|
|
e660fe9e1e | ||
|
|
23c1d12e73 | ||
|
|
9cf2785626 | ||
|
|
b8b65c7e3e | ||
|
|
dcb467280a | ||
|
|
6aa802b42d | ||
|
|
d78f6ca589 | ||
|
|
493f8e0cc0 | ||
|
|
119563c553 | ||
|
|
2d61e6af66 | ||
|
|
aa1be934a9 | ||
|
|
f9c98b0a60 | ||
|
|
bd66fa3bf5 | ||
|
|
380f191f6a | ||
|
|
7e217b5fba | ||
|
|
c4a516a858 | ||
|
|
bdf181e348 | ||
|
|
f4ea1343b4 | ||
|
|
a37ccddd38 | ||
|
|
243ef8c0be | ||
|
|
00d099383b | ||
|
|
dda3f0b8e9 | ||
|
|
00f4d8b1ee | ||
|
|
2f5198d533 | ||
|
|
148261f876 | ||
|
|
60843b3bb9 | ||
|
|
2ad9a525bd | ||
|
|
78e9f21439 | ||
|
|
a66d60eaea | ||
|
|
3aa3c13477 | ||
|
|
cc850522e6 | ||
|
|
6d28f57f88 | ||
|
|
563e0a7cd4 | ||
|
|
2f2f857e98 | ||
|
|
251c52a2ee | ||
|
|
7528bd343b | ||
|
|
06d9f279ac | ||
|
|
044403b829 | ||
|
|
5a24dd3b49 | ||
|
|
3189b3c7a5 | ||
|
|
3bf1c6a282 | ||
|
|
7c7309c3ab | ||
|
|
da777da476 | ||
|
|
3d0c0a11ed | ||
|
|
e545269b93 | ||
|
|
141ca76647 | ||
|
|
94557830f5 | ||
|
|
49acb7faba | ||
|
|
1904f67662 | ||
|
|
5b2bf38344 | ||
|
|
494c38a153 | ||
|
|
dd4b85cbfe | ||
|
|
8f7b54a5a4 | ||
|
|
cec502340e | ||
|
|
64e27c7fb0 | ||
|
|
b2bbd31548 | ||
|
|
17df92a07c | ||
|
|
2b749b5ab7 | ||
|
|
28e3402d88 | ||
|
|
d96bb061e0 | ||
|
|
e6def804f8 | ||
|
|
a5be48c07c | ||
|
|
fe3909f594 | ||
|
|
f37d91a530 | ||
|
|
614ef78771 | ||
|
|
fb294fc03c | ||
|
|
8c7e7c3d48 | ||
|
|
98b6280652 | ||
|
|
7c4c2d6382 | ||
|
|
1a29ea302e | ||
|
|
be39fce741 | ||
|
|
4fed2e6e5f | ||
|
|
14ae5809b0 | ||
|
|
0f66aa47c9 | ||
|
|
cf85d300f4 | ||
|
|
91d60e56df | ||
|
|
1d3681beb4 | ||
|
|
0b403cf329 | ||
|
|
8ba75899e3 | ||
|
|
4d4ed72159 | ||
|
|
b72bf072b3 | ||
|
|
4edcb54b31 | ||
|
|
eae7fc0e53 | ||
|
|
fddacd4410 | ||
|
|
de6c4b9a30 | ||
|
|
6990e34138 | ||
|
|
d9883697ef | ||
|
|
05a26ff8b2 | ||
|
|
84bb082d44 | ||
|
|
a0db94d84f | ||
|
|
0367b4ecd7 | ||
|
|
dbc425dce6 | ||
|
|
116c017c6d | ||
|
|
9c387475f0 | ||
|
|
0765c21cef | ||
|
|
2871038584 | ||
|
|
340885f939 | ||
|
|
1e32e47f54 | ||
|
|
3c759f3b01 | ||
|
|
6615f34d20 | ||
|
|
3a4aac1ee4 | ||
|
|
4d6c092615 | ||
|
|
93421a1dc9 | ||
|
|
209458a856 | ||
|
|
82bd94620e | ||
|
|
af9f017871 | ||
|
|
2f8922ea87 | ||
|
|
0ea936f3fe | ||
|
|
d1870ee0a8 | ||
|
|
d2151690ad | ||
|
|
dff373e7d5 | ||
|
|
0aec2a664f | ||
|
|
723b696393 | ||
|
|
f5f89eb4e4 | ||
|
|
df15332c7f | ||
|
|
61d9e5a869 | ||
|
|
9628b66a97 | ||
|
|
5e041366d4 | ||
|
|
3ecae8d72c | ||
|
|
5709ce9d82 | ||
|
|
ce3c334ac5 | ||
|
|
2ed5aa8730 | ||
|
|
8480a63dda | ||
|
|
132a1695f3 | ||
|
|
21775630c3 | ||
|
|
eac2ef7c6d | ||
|
|
386997f646 | ||
|
|
637b90ad62 | ||
|
|
95d755c2ec | ||
|
|
781aeebef6 | ||
|
|
5e133fd51a | ||
|
|
85f62a3b9d | ||
|
|
a32de58c8b | ||
|
|
1cb2ea6c17 | ||
|
|
6a37ab7af2 | ||
|
|
e0f0aaf767 | ||
|
|
3d7c5b050a | ||
|
|
6bc57c255f | ||
|
|
b82edfe688 | ||
|
|
6b32eb3441 | ||
|
|
23a07fa8a5 | ||
|
|
b019faedd2 | ||
|
|
4430433a10 | ||
|
|
f52cd29e7b | ||
|
|
6a44e593a6 | ||
|
|
f7065fe034 | ||
|
|
0a247956f7 | ||
|
|
03836acded | ||
|
|
b5fb277982 | ||
|
|
e523d3c166 | ||
|
|
41477e4aa6 | ||
|
|
fbaf42a8c4 | ||
|
|
1c3668047b | ||
|
|
7d78c69b6e |
4
.github/ISSUE_TEMPLATE/bug.yml
vendored
4
.github/ISSUE_TEMPLATE/bug.yml
vendored
@@ -39,6 +39,10 @@ body:
|
|||||||
- 1.17
|
- 1.17
|
||||||
- 1.17.1
|
- 1.17.1
|
||||||
- 1.18
|
- 1.18
|
||||||
|
- 1.19
|
||||||
|
- 1.20
|
||||||
|
- 1.21
|
||||||
|
- 1.22
|
||||||
validations:
|
validations:
|
||||||
required: true
|
required: true
|
||||||
- type: input
|
- type: input
|
||||||
|
|||||||
1
.gitignore
vendored
1
.gitignore
vendored
@@ -1,5 +1,6 @@
|
|||||||
|
|
||||||
build/
|
build/
|
||||||
|
libs/
|
||||||
|
|
||||||
.gradle/
|
.gradle/
|
||||||
|
|
||||||
|
|||||||
@@ -11,6 +11,8 @@ development.
|
|||||||
|
|
||||||
Consider supporting our development by buying Iris on spigot! We work hard to make Iris the best it can be for everyone.
|
Consider supporting our development by buying Iris on spigot! We work hard to make Iris the best it can be for everyone.
|
||||||
|
|
||||||
|
## Preface: if you need help compiling and you are a developer / intend to help out in the community or with development we would love to help you regardless in the discord! however do not come to the discord asking for free copies, or a tutorial on how to compile.
|
||||||
|
|
||||||
### Command Line Builds
|
### Command Line Builds
|
||||||
|
|
||||||
1. Install [Java JDK 17](https://www.oracle.com/java/technologies/javase/jdk17-archive-downloads.html)
|
1. Install [Java JDK 17](https://www.oracle.com/java/technologies/javase/jdk17-archive-downloads.html)
|
||||||
|
|||||||
49
build.gradle
49
build.gradle
@@ -24,21 +24,22 @@ plugins {
|
|||||||
id "de.undercouch.download" version "5.0.1"
|
id "de.undercouch.download" version "5.0.1"
|
||||||
}
|
}
|
||||||
|
|
||||||
version '2.2.1-1.19' // Needs to be version specific
|
version '2.7.6-1.20.1'
|
||||||
def nmsVersion = "1.19"
|
def nmsVersion = '1.20.1' //[NMS]
|
||||||
def apiVersion = '1.19'
|
def apiVersion = '1.20'
|
||||||
def spigotJarVersion = '1.19-R0.1-SNAPSHOT'
|
def specialSourceVersion = '1.11.0' //[NMS]
|
||||||
|
def spigotJarVersion = '1.20.1-R0.1-SNAPSHOT' //[NMS]
|
||||||
def name = getRootProject().getName() // Defined in settings.gradle
|
def name = getRootProject().getName() // Defined in settings.gradle
|
||||||
def main = 'com.volmit.iris.Iris'
|
def main = 'com.volmit.iris.Iris'
|
||||||
|
|
||||||
// ADD YOURSELF AS A NEW LINE IF YOU WANT YOUR OWN BUILD TASK GENERATED
|
// ADD YOURSELF AS A NEW LINE IF YOU WANT YOUR OWN BUILD TASK GENERATED
|
||||||
// ======================== WINDOWS =============================
|
// ======================== WINDOWS =============================
|
||||||
registerCustomOutputTask('Cyberpwn', 'C://Users/cyberpwn/Documents/development/server/plugins')
|
registerCustomOutputTask('Cyberpwn', 'C://Users/cyberpwn/Documents/development/server/plugins')
|
||||||
registerCustomOutputTask('Psycho', 'D://Dan/MinecraftDevelopment/server/plugins')
|
registerCustomOutputTask('Psycho', 'C://Dan/MinecraftDevelopment/Server/plugins')
|
||||||
registerCustomOutputTask('ArcaneArts', 'C://Users/arcane/Documents/development/server/plugins')
|
registerCustomOutputTask('ArcaneArts', 'C://Users/arcane/Documents/development/server/plugins')
|
||||||
registerCustomOutputTask('Coco', 'D://Documents/MC/plugins')
|
registerCustomOutputTask('Coco', 'D://mcsm/plugins')
|
||||||
registerCustomOutputTask('Strange', 'D://Servers/1.17 Test Server/plugins')
|
registerCustomOutputTask('Strange', 'D://Servers/1.17 Test Server/plugins')
|
||||||
registerCustomOutputTask('Vatuu', 'D://Minecraft/Servers/1.19/plugins')
|
registerCustomOutputTask('Vatuu', 'D://Minecraft/Servers/1.19.4/plugins')
|
||||||
// ========================== UNIX ==============================
|
// ========================== UNIX ==============================
|
||||||
registerCustomOutputTaskUnix('CyberpwnLT', '/Users/danielmills/development/server/plugins')
|
registerCustomOutputTaskUnix('CyberpwnLT', '/Users/danielmills/development/server/plugins')
|
||||||
registerCustomOutputTaskUnix('PsychoLT', '/Users/brianfopiano/Desktop/REMOTES/RemoteMinecraft/plugins')
|
registerCustomOutputTaskUnix('PsychoLT', '/Users/brianfopiano/Desktop/REMOTES/RemoteMinecraft/plugins')
|
||||||
@@ -73,11 +74,16 @@ repositories {
|
|||||||
includeGroup("org.spigotmc")
|
includeGroup("org.spigotmc")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
maven { url "https://dl.cloudsmith.io/public/arcane/archive/maven/" }
|
|
||||||
maven { url "https://maven.enginehub.org/repo/" }
|
|
||||||
mavenCentral()
|
mavenCentral()
|
||||||
mavenLocal()
|
maven { url "https://arcanearts.jfrog.io/artifactory/archives" }
|
||||||
|
maven { url "https://mvn.lumine.io/repository/maven-public/" }
|
||||||
maven { url "https://jitpack.io"}
|
maven { url "https://jitpack.io"}
|
||||||
|
|
||||||
|
maven { url "https://s01.oss.sonatype.org/content/repositories/snapshots" }
|
||||||
|
maven { url "https://mvn.lumine.io/repository/maven/" }
|
||||||
|
maven { url "https://repo.triumphteam.dev/snapshots" }
|
||||||
|
maven { url "https://repo.mineinabyss.com/releases" }
|
||||||
|
maven { url = 'https://hub.jeff-media.com/nexus/repository/jeff-media-public/' }
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -124,18 +130,23 @@ dependencies {
|
|||||||
// Provided or Classpath
|
// Provided or Classpath
|
||||||
compileOnly 'org.projectlombok:lombok:1.18.24'
|
compileOnly 'org.projectlombok:lombok:1.18.24'
|
||||||
annotationProcessor 'org.projectlombok:lombok:1.18.24'
|
annotationProcessor 'org.projectlombok:lombok:1.18.24'
|
||||||
implementation 'org.spigotmc:spigot-api:1.19-R0.1-SNAPSHOT'
|
implementation 'org.spigotmc:spigot-api:1.20.1-R0.1-SNAPSHOT'
|
||||||
implementation 'me.clip:placeholderapi:2.11.1'
|
implementation 'org.bukkit:craftbukkit:1.20.1-R0.1-SNAPSHOT:remapped-mojang' //[NMS]
|
||||||
implementation 'io.th0rgal:oraxen:1.94.0'
|
|
||||||
implementation 'org.bukkit:craftbukkit:1.19-R0.1-SNAPSHOT:remapped-mojang'
|
// Third Party Integrations
|
||||||
implementation 'com.github.LoneDev6:api-itemsadder:3.1.0b'
|
implementation 'com.ticxo.playeranimator:PlayerAnimator:R1.2.7'
|
||||||
|
implementation 'com.github.oraxen:oraxen:1.158.0'
|
||||||
|
implementation 'com.github.LoneDev6:api-itemsadder:3.4.1-r4'
|
||||||
|
implementation 'me.clip:placeholderapi:2.11.3'
|
||||||
|
//implementation files('libs/CustomItems.jar')
|
||||||
|
|
||||||
// Shaded
|
// Shaded
|
||||||
implementation 'com.dfsek:Paralithic:0.4.0'
|
implementation 'com.dfsek:Paralithic:0.4.0'
|
||||||
implementation 'io.papermc:paperlib:1.0.5'
|
implementation 'io.papermc:paperlib:1.0.5'
|
||||||
implementation "net.kyori:adventure-text-minimessage:4.11.0"
|
implementation "net.kyori:adventure-text-minimessage:4.13.1"
|
||||||
implementation 'net.kyori:adventure-platform-bukkit:4.1.0'
|
implementation 'net.kyori:adventure-platform-bukkit:4.3.0'
|
||||||
implementation 'net.kyori:adventure-api:4.11.0'
|
implementation 'net.kyori:adventure-api:4.13.1'
|
||||||
|
implementation 'io.lumine:Mythic-Dist:5.2.1'
|
||||||
|
|
||||||
// Dynamically Loaded
|
// Dynamically Loaded
|
||||||
implementation 'io.timeandspace:smoothie-map:2.0.2'
|
implementation 'io.timeandspace:smoothie-map:2.0.2'
|
||||||
@@ -194,7 +205,7 @@ task downloadBuildtools(type: Download) {
|
|||||||
|
|
||||||
task downloadSpecialSource(type: Download) {
|
task downloadSpecialSource(type: Download) {
|
||||||
group "remapping"
|
group "remapping"
|
||||||
src 'https://repo.maven.apache.org/maven2/net/md-5/SpecialSource/1.10.0/SpecialSource-1.10.0-shaded.jar'
|
src 'https://repo.maven.apache.org/maven2/net/md-5/SpecialSource/' + specialSourceVersion + '/SpecialSource-'+specialSourceVersion+'-shaded.jar'
|
||||||
dest specialSourceJar
|
dest specialSourceJar
|
||||||
onlyIf {
|
onlyIf {
|
||||||
!specialSourceJar.exists()
|
!specialSourceJar.exists()
|
||||||
|
|||||||
3
gource.bat
Normal file
3
gource.bat
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
@echo off
|
||||||
|
cd gource
|
||||||
|
gource -f -a 1 -s 0.01 -t 100000 --colour-images --max-file-lag 35 --title MyGuide --user-scale 1.67 --max-user-speed 725 --filename-time 11 -title Chimera --user-friction 2.5 --padding 1.2 --user-scale 1.25 --filename-time 2 --bloom-intensity 0.1 --bloom-multiplier 3 --hide filenames,dirnames
|
||||||
674
gource/COPYING.txt
Normal file
674
gource/COPYING.txt
Normal file
@@ -0,0 +1,674 @@
|
|||||||
|
GNU GENERAL PUBLIC LICENSE
|
||||||
|
Version 3, 29 June 2007
|
||||||
|
|
||||||
|
Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
|
||||||
|
Everyone is permitted to copy and distribute verbatim copies
|
||||||
|
of this license document, but changing it is not allowed.
|
||||||
|
|
||||||
|
Preamble
|
||||||
|
|
||||||
|
The GNU General Public License is a free, copyleft license for
|
||||||
|
software and other kinds of works.
|
||||||
|
|
||||||
|
The licenses for most software and other practical works are designed
|
||||||
|
to take away your freedom to share and change the works. By contrast,
|
||||||
|
the GNU General Public License is intended to guarantee your freedom to
|
||||||
|
share and change all versions of a program--to make sure it remains free
|
||||||
|
software for all its users. We, the Free Software Foundation, use the
|
||||||
|
GNU General Public License for most of our software; it applies also to
|
||||||
|
any other work released this way by its authors. You can apply it to
|
||||||
|
your programs, too.
|
||||||
|
|
||||||
|
When we speak of free software, we are referring to freedom, not
|
||||||
|
price. Our General Public Licenses are designed to make sure that you
|
||||||
|
have the freedom to distribute copies of free software (and charge for
|
||||||
|
them if you wish), that you receive source code or can get it if you
|
||||||
|
want it, that you can change the software or use pieces of it in new
|
||||||
|
free programs, and that you know you can do these things.
|
||||||
|
|
||||||
|
To protect your rights, we need to prevent others from denying you
|
||||||
|
these rights or asking you to surrender the rights. Therefore, you have
|
||||||
|
certain responsibilities if you distribute copies of the software, or if
|
||||||
|
you modify it: responsibilities to respect the freedom of others.
|
||||||
|
|
||||||
|
For example, if you distribute copies of such a program, whether
|
||||||
|
gratis or for a fee, you must pass on to the recipients the same
|
||||||
|
freedoms that you received. You must make sure that they, too, receive
|
||||||
|
or can get the source code. And you must show them these terms so they
|
||||||
|
know their rights.
|
||||||
|
|
||||||
|
Developers that use the GNU GPL protect your rights with two steps:
|
||||||
|
(1) assert copyright on the software, and (2) offer you this License
|
||||||
|
giving you legal permission to copy, distribute and/or modify it.
|
||||||
|
|
||||||
|
For the developers' and authors' protection, the GPL clearly explains
|
||||||
|
that there is no warranty for this free software. For both users' and
|
||||||
|
authors' sake, the GPL requires that modified versions be marked as
|
||||||
|
changed, so that their problems will not be attributed erroneously to
|
||||||
|
authors of previous versions.
|
||||||
|
|
||||||
|
Some devices are designed to deny users access to install or run
|
||||||
|
modified versions of the software inside them, although the manufacturer
|
||||||
|
can do so. This is fundamentally incompatible with the aim of
|
||||||
|
protecting users' freedom to change the software. The systematic
|
||||||
|
pattern of such abuse occurs in the area of products for individuals to
|
||||||
|
use, which is precisely where it is most unacceptable. Therefore, we
|
||||||
|
have designed this version of the GPL to prohibit the practice for those
|
||||||
|
products. If such problems arise substantially in other domains, we
|
||||||
|
stand ready to extend this provision to those domains in future versions
|
||||||
|
of the GPL, as needed to protect the freedom of users.
|
||||||
|
|
||||||
|
Finally, every program is threatened constantly by software patents.
|
||||||
|
States should not allow patents to restrict development and use of
|
||||||
|
software on general-purpose computers, but in those that do, we wish to
|
||||||
|
avoid the special danger that patents applied to a free program could
|
||||||
|
make it effectively proprietary. To prevent this, the GPL assures that
|
||||||
|
patents cannot be used to render the program non-free.
|
||||||
|
|
||||||
|
The precise terms and conditions for copying, distribution and
|
||||||
|
modification follow.
|
||||||
|
|
||||||
|
TERMS AND CONDITIONS
|
||||||
|
|
||||||
|
0. Definitions.
|
||||||
|
|
||||||
|
"This License" refers to version 3 of the GNU General Public License.
|
||||||
|
|
||||||
|
"Copyright" also means copyright-like laws that apply to other kinds of
|
||||||
|
works, such as semiconductor masks.
|
||||||
|
|
||||||
|
"The Program" refers to any copyrightable work licensed under this
|
||||||
|
License. Each licensee is addressed as "you". "Licensees" and
|
||||||
|
"recipients" may be individuals or organizations.
|
||||||
|
|
||||||
|
To "modify" a work means to copy from or adapt all or part of the work
|
||||||
|
in a fashion requiring copyright permission, other than the making of an
|
||||||
|
exact copy. The resulting work is called a "modified version" of the
|
||||||
|
earlier work or a work "based on" the earlier work.
|
||||||
|
|
||||||
|
A "covered work" means either the unmodified Program or a work based
|
||||||
|
on the Program.
|
||||||
|
|
||||||
|
To "propagate" a work means to do anything with it that, without
|
||||||
|
permission, would make you directly or secondarily liable for
|
||||||
|
infringement under applicable copyright law, except executing it on a
|
||||||
|
computer or modifying a private copy. Propagation includes copying,
|
||||||
|
distribution (with or without modification), making available to the
|
||||||
|
public, and in some countries other activities as well.
|
||||||
|
|
||||||
|
To "convey" a work means any kind of propagation that enables other
|
||||||
|
parties to make or receive copies. Mere interaction with a user through
|
||||||
|
a computer network, with no transfer of a copy, is not conveying.
|
||||||
|
|
||||||
|
An interactive user interface displays "Appropriate Legal Notices"
|
||||||
|
to the extent that it includes a convenient and prominently visible
|
||||||
|
feature that (1) displays an appropriate copyright notice, and (2)
|
||||||
|
tells the user that there is no warranty for the work (except to the
|
||||||
|
extent that warranties are provided), that licensees may convey the
|
||||||
|
work under this License, and how to view a copy of this License. If
|
||||||
|
the interface presents a list of user commands or options, such as a
|
||||||
|
menu, a prominent item in the list meets this criterion.
|
||||||
|
|
||||||
|
1. Source Code.
|
||||||
|
|
||||||
|
The "source code" for a work means the preferred form of the work
|
||||||
|
for making modifications to it. "Object code" means any non-source
|
||||||
|
form of a work.
|
||||||
|
|
||||||
|
A "Standard Interface" means an interface that either is an official
|
||||||
|
standard defined by a recognized standards body, or, in the case of
|
||||||
|
interfaces specified for a particular programming language, one that
|
||||||
|
is widely used among developers working in that language.
|
||||||
|
|
||||||
|
The "System Libraries" of an executable work include anything, other
|
||||||
|
than the work as a whole, that (a) is included in the normal form of
|
||||||
|
packaging a Major Component, but which is not part of that Major
|
||||||
|
Component, and (b) serves only to enable use of the work with that
|
||||||
|
Major Component, or to implement a Standard Interface for which an
|
||||||
|
implementation is available to the public in source code form. A
|
||||||
|
"Major Component", in this context, means a major essential component
|
||||||
|
(kernel, window system, and so on) of the specific operating system
|
||||||
|
(if any) on which the executable work runs, or a compiler used to
|
||||||
|
produce the work, or an object code interpreter used to run it.
|
||||||
|
|
||||||
|
The "Corresponding Source" for a work in object code form means all
|
||||||
|
the source code needed to generate, install, and (for an executable
|
||||||
|
work) run the object code and to modify the work, including scripts to
|
||||||
|
control those activities. However, it does not include the work's
|
||||||
|
System Libraries, or general-purpose tools or generally available free
|
||||||
|
programs which are used unmodified in performing those activities but
|
||||||
|
which are not part of the work. For example, Corresponding Source
|
||||||
|
includes interface definition files associated with source files for
|
||||||
|
the work, and the source code for shared libraries and dynamically
|
||||||
|
linked subprograms that the work is specifically designed to require,
|
||||||
|
such as by intimate data communication or control flow between those
|
||||||
|
subprograms and other parts of the work.
|
||||||
|
|
||||||
|
The Corresponding Source need not include anything that users
|
||||||
|
can regenerate automatically from other parts of the Corresponding
|
||||||
|
Source.
|
||||||
|
|
||||||
|
The Corresponding Source for a work in source code form is that
|
||||||
|
same work.
|
||||||
|
|
||||||
|
2. Basic Permissions.
|
||||||
|
|
||||||
|
All rights granted under this License are granted for the term of
|
||||||
|
copyright on the Program, and are irrevocable provided the stated
|
||||||
|
conditions are met. This License explicitly affirms your unlimited
|
||||||
|
permission to run the unmodified Program. The output from running a
|
||||||
|
covered work is covered by this License only if the output, given its
|
||||||
|
content, constitutes a covered work. This License acknowledges your
|
||||||
|
rights of fair use or other equivalent, as provided by copyright law.
|
||||||
|
|
||||||
|
You may make, run and propagate covered works that you do not
|
||||||
|
convey, without conditions so long as your license otherwise remains
|
||||||
|
in force. You may convey covered works to others for the sole purpose
|
||||||
|
of having them make modifications exclusively for you, or provide you
|
||||||
|
with facilities for running those works, provided that you comply with
|
||||||
|
the terms of this License in conveying all material for which you do
|
||||||
|
not control copyright. Those thus making or running the covered works
|
||||||
|
for you must do so exclusively on your behalf, under your direction
|
||||||
|
and control, on terms that prohibit them from making any copies of
|
||||||
|
your copyrighted material outside their relationship with you.
|
||||||
|
|
||||||
|
Conveying under any other circumstances is permitted solely under
|
||||||
|
the conditions stated below. Sublicensing is not allowed; section 10
|
||||||
|
makes it unnecessary.
|
||||||
|
|
||||||
|
3. Protecting Users' Legal Rights From Anti-Circumvention Law.
|
||||||
|
|
||||||
|
No covered work shall be deemed part of an effective technological
|
||||||
|
measure under any applicable law fulfilling obligations under article
|
||||||
|
11 of the WIPO copyright treaty adopted on 20 December 1996, or
|
||||||
|
similar laws prohibiting or restricting circumvention of such
|
||||||
|
measures.
|
||||||
|
|
||||||
|
When you convey a covered work, you waive any legal power to forbid
|
||||||
|
circumvention of technological measures to the extent such circumvention
|
||||||
|
is effected by exercising rights under this License with respect to
|
||||||
|
the covered work, and you disclaim any intention to limit operation or
|
||||||
|
modification of the work as a means of enforcing, against the work's
|
||||||
|
users, your or third parties' legal rights to forbid circumvention of
|
||||||
|
technological measures.
|
||||||
|
|
||||||
|
4. Conveying Verbatim Copies.
|
||||||
|
|
||||||
|
You may convey verbatim copies of the Program's source code as you
|
||||||
|
receive it, in any medium, provided that you conspicuously and
|
||||||
|
appropriately publish on each copy an appropriate copyright notice;
|
||||||
|
keep intact all notices stating that this License and any
|
||||||
|
non-permissive terms added in accord with section 7 apply to the code;
|
||||||
|
keep intact all notices of the absence of any warranty; and give all
|
||||||
|
recipients a copy of this License along with the Program.
|
||||||
|
|
||||||
|
You may charge any price or no price for each copy that you convey,
|
||||||
|
and you may offer support or warranty protection for a fee.
|
||||||
|
|
||||||
|
5. Conveying Modified Source Versions.
|
||||||
|
|
||||||
|
You may convey a work based on the Program, or the modifications to
|
||||||
|
produce it from the Program, in the form of source code under the
|
||||||
|
terms of section 4, provided that you also meet all of these conditions:
|
||||||
|
|
||||||
|
a) The work must carry prominent notices stating that you modified
|
||||||
|
it, and giving a relevant date.
|
||||||
|
|
||||||
|
b) The work must carry prominent notices stating that it is
|
||||||
|
released under this License and any conditions added under section
|
||||||
|
7. This requirement modifies the requirement in section 4 to
|
||||||
|
"keep intact all notices".
|
||||||
|
|
||||||
|
c) You must license the entire work, as a whole, under this
|
||||||
|
License to anyone who comes into possession of a copy. This
|
||||||
|
License will therefore apply, along with any applicable section 7
|
||||||
|
additional terms, to the whole of the work, and all its parts,
|
||||||
|
regardless of how they are packaged. This License gives no
|
||||||
|
permission to license the work in any other way, but it does not
|
||||||
|
invalidate such permission if you have separately received it.
|
||||||
|
|
||||||
|
d) If the work has interactive user interfaces, each must display
|
||||||
|
Appropriate Legal Notices; however, if the Program has interactive
|
||||||
|
interfaces that do not display Appropriate Legal Notices, your
|
||||||
|
work need not make them do so.
|
||||||
|
|
||||||
|
A compilation of a covered work with other separate and independent
|
||||||
|
works, which are not by their nature extensions of the covered work,
|
||||||
|
and which are not combined with it such as to form a larger program,
|
||||||
|
in or on a volume of a storage or distribution medium, is called an
|
||||||
|
"aggregate" if the compilation and its resulting copyright are not
|
||||||
|
used to limit the access or legal rights of the compilation's users
|
||||||
|
beyond what the individual works permit. Inclusion of a covered work
|
||||||
|
in an aggregate does not cause this License to apply to the other
|
||||||
|
parts of the aggregate.
|
||||||
|
|
||||||
|
6. Conveying Non-Source Forms.
|
||||||
|
|
||||||
|
You may convey a covered work in object code form under the terms
|
||||||
|
of sections 4 and 5, provided that you also convey the
|
||||||
|
machine-readable Corresponding Source under the terms of this License,
|
||||||
|
in one of these ways:
|
||||||
|
|
||||||
|
a) Convey the object code in, or embodied in, a physical product
|
||||||
|
(including a physical distribution medium), accompanied by the
|
||||||
|
Corresponding Source fixed on a durable physical medium
|
||||||
|
customarily used for software interchange.
|
||||||
|
|
||||||
|
b) Convey the object code in, or embodied in, a physical product
|
||||||
|
(including a physical distribution medium), accompanied by a
|
||||||
|
written offer, valid for at least three years and valid for as
|
||||||
|
long as you offer spare parts or customer support for that product
|
||||||
|
model, to give anyone who possesses the object code either (1) a
|
||||||
|
copy of the Corresponding Source for all the software in the
|
||||||
|
product that is covered by this License, on a durable physical
|
||||||
|
medium customarily used for software interchange, for a price no
|
||||||
|
more than your reasonable cost of physically performing this
|
||||||
|
conveying of source, or (2) access to copy the
|
||||||
|
Corresponding Source from a network server at no charge.
|
||||||
|
|
||||||
|
c) Convey individual copies of the object code with a copy of the
|
||||||
|
written offer to provide the Corresponding Source. This
|
||||||
|
alternative is allowed only occasionally and noncommercially, and
|
||||||
|
only if you received the object code with such an offer, in accord
|
||||||
|
with subsection 6b.
|
||||||
|
|
||||||
|
d) Convey the object code by offering access from a designated
|
||||||
|
place (gratis or for a charge), and offer equivalent access to the
|
||||||
|
Corresponding Source in the same way through the same place at no
|
||||||
|
further charge. You need not require recipients to copy the
|
||||||
|
Corresponding Source along with the object code. If the place to
|
||||||
|
copy the object code is a network server, the Corresponding Source
|
||||||
|
may be on a different server (operated by you or a third party)
|
||||||
|
that supports equivalent copying facilities, provided you maintain
|
||||||
|
clear directions next to the object code saying where to find the
|
||||||
|
Corresponding Source. Regardless of what server hosts the
|
||||||
|
Corresponding Source, you remain obligated to ensure that it is
|
||||||
|
available for as long as needed to satisfy these requirements.
|
||||||
|
|
||||||
|
e) Convey the object code using peer-to-peer transmission, provided
|
||||||
|
you inform other peers where the object code and Corresponding
|
||||||
|
Source of the work are being offered to the general public at no
|
||||||
|
charge under subsection 6d.
|
||||||
|
|
||||||
|
A separable portion of the object code, whose source code is excluded
|
||||||
|
from the Corresponding Source as a System Library, need not be
|
||||||
|
included in conveying the object code work.
|
||||||
|
|
||||||
|
A "User Product" is either (1) a "consumer product", which means any
|
||||||
|
tangible personal property which is normally used for personal, family,
|
||||||
|
or household purposes, or (2) anything designed or sold for incorporation
|
||||||
|
into a dwelling. In determining whether a product is a consumer product,
|
||||||
|
doubtful cases shall be resolved in favor of coverage. For a particular
|
||||||
|
product received by a particular user, "normally used" refers to a
|
||||||
|
typical or common use of that class of product, regardless of the status
|
||||||
|
of the particular user or of the way in which the particular user
|
||||||
|
actually uses, or expects or is expected to use, the product. A product
|
||||||
|
is a consumer product regardless of whether the product has substantial
|
||||||
|
commercial, industrial or non-consumer uses, unless such uses represent
|
||||||
|
the only significant mode of use of the product.
|
||||||
|
|
||||||
|
"Installation Information" for a User Product means any methods,
|
||||||
|
procedures, authorization keys, or other information required to install
|
||||||
|
and execute modified versions of a covered work in that User Product from
|
||||||
|
a modified version of its Corresponding Source. The information must
|
||||||
|
suffice to ensure that the continued functioning of the modified object
|
||||||
|
code is in no case prevented or interfered with solely because
|
||||||
|
modification has been made.
|
||||||
|
|
||||||
|
If you convey an object code work under this section in, or with, or
|
||||||
|
specifically for use in, a User Product, and the conveying occurs as
|
||||||
|
part of a transaction in which the right of possession and use of the
|
||||||
|
User Product is transferred to the recipient in perpetuity or for a
|
||||||
|
fixed term (regardless of how the transaction is characterized), the
|
||||||
|
Corresponding Source conveyed under this section must be accompanied
|
||||||
|
by the Installation Information. But this requirement does not apply
|
||||||
|
if neither you nor any third party retains the ability to install
|
||||||
|
modified object code on the User Product (for example, the work has
|
||||||
|
been installed in ROM).
|
||||||
|
|
||||||
|
The requirement to provide Installation Information does not include a
|
||||||
|
requirement to continue to provide support service, warranty, or updates
|
||||||
|
for a work that has been modified or installed by the recipient, or for
|
||||||
|
the User Product in which it has been modified or installed. Access to a
|
||||||
|
network may be denied when the modification itself materially and
|
||||||
|
adversely affects the operation of the network or violates the rules and
|
||||||
|
protocols for communication across the network.
|
||||||
|
|
||||||
|
Corresponding Source conveyed, and Installation Information provided,
|
||||||
|
in accord with this section must be in a format that is publicly
|
||||||
|
documented (and with an implementation available to the public in
|
||||||
|
source code form), and must require no special password or key for
|
||||||
|
unpacking, reading or copying.
|
||||||
|
|
||||||
|
7. Additional Terms.
|
||||||
|
|
||||||
|
"Additional permissions" are terms that supplement the terms of this
|
||||||
|
License by making exceptions from one or more of its conditions.
|
||||||
|
Additional permissions that are applicable to the entire Program shall
|
||||||
|
be treated as though they were included in this License, to the extent
|
||||||
|
that they are valid under applicable law. If additional permissions
|
||||||
|
apply only to part of the Program, that part may be used separately
|
||||||
|
under those permissions, but the entire Program remains governed by
|
||||||
|
this License without regard to the additional permissions.
|
||||||
|
|
||||||
|
When you convey a copy of a covered work, you may at your option
|
||||||
|
remove any additional permissions from that copy, or from any part of
|
||||||
|
it. (Additional permissions may be written to require their own
|
||||||
|
removal in certain cases when you modify the work.) You may place
|
||||||
|
additional permissions on material, added by you to a covered work,
|
||||||
|
for which you have or can give appropriate copyright permission.
|
||||||
|
|
||||||
|
Notwithstanding any other provision of this License, for material you
|
||||||
|
add to a covered work, you may (if authorized by the copyright holders of
|
||||||
|
that material) supplement the terms of this License with terms:
|
||||||
|
|
||||||
|
a) Disclaiming warranty or limiting liability differently from the
|
||||||
|
terms of sections 15 and 16 of this License; or
|
||||||
|
|
||||||
|
b) Requiring preservation of specified reasonable legal notices or
|
||||||
|
author attributions in that material or in the Appropriate Legal
|
||||||
|
Notices displayed by works containing it; or
|
||||||
|
|
||||||
|
c) Prohibiting misrepresentation of the origin of that material, or
|
||||||
|
requiring that modified versions of such material be marked in
|
||||||
|
reasonable ways as different from the original version; or
|
||||||
|
|
||||||
|
d) Limiting the use for publicity purposes of names of licensors or
|
||||||
|
authors of the material; or
|
||||||
|
|
||||||
|
e) Declining to grant rights under trademark law for use of some
|
||||||
|
trade names, trademarks, or service marks; or
|
||||||
|
|
||||||
|
f) Requiring indemnification of licensors and authors of that
|
||||||
|
material by anyone who conveys the material (or modified versions of
|
||||||
|
it) with contractual assumptions of liability to the recipient, for
|
||||||
|
any liability that these contractual assumptions directly impose on
|
||||||
|
those licensors and authors.
|
||||||
|
|
||||||
|
All other non-permissive additional terms are considered "further
|
||||||
|
restrictions" within the meaning of section 10. If the Program as you
|
||||||
|
received it, or any part of it, contains a notice stating that it is
|
||||||
|
governed by this License along with a term that is a further
|
||||||
|
restriction, you may remove that term. If a license document contains
|
||||||
|
a further restriction but permits relicensing or conveying under this
|
||||||
|
License, you may add to a covered work material governed by the terms
|
||||||
|
of that license document, provided that the further restriction does
|
||||||
|
not survive such relicensing or conveying.
|
||||||
|
|
||||||
|
If you add terms to a covered work in accord with this section, you
|
||||||
|
must place, in the relevant source files, a statement of the
|
||||||
|
additional terms that apply to those files, or a notice indicating
|
||||||
|
where to find the applicable terms.
|
||||||
|
|
||||||
|
Additional terms, permissive or non-permissive, may be stated in the
|
||||||
|
form of a separately written license, or stated as exceptions;
|
||||||
|
the above requirements apply either way.
|
||||||
|
|
||||||
|
8. Termination.
|
||||||
|
|
||||||
|
You may not propagate or modify a covered work except as expressly
|
||||||
|
provided under this License. Any attempt otherwise to propagate or
|
||||||
|
modify it is void, and will automatically terminate your rights under
|
||||||
|
this License (including any patent licenses granted under the third
|
||||||
|
paragraph of section 11).
|
||||||
|
|
||||||
|
However, if you cease all violation of this License, then your
|
||||||
|
license from a particular copyright holder is reinstated (a)
|
||||||
|
provisionally, unless and until the copyright holder explicitly and
|
||||||
|
finally terminates your license, and (b) permanently, if the copyright
|
||||||
|
holder fails to notify you of the violation by some reasonable means
|
||||||
|
prior to 60 days after the cessation.
|
||||||
|
|
||||||
|
Moreover, your license from a particular copyright holder is
|
||||||
|
reinstated permanently if the copyright holder notifies you of the
|
||||||
|
violation by some reasonable means, this is the first time you have
|
||||||
|
received notice of violation of this License (for any work) from that
|
||||||
|
copyright holder, and you cure the violation prior to 30 days after
|
||||||
|
your receipt of the notice.
|
||||||
|
|
||||||
|
Termination of your rights under this section does not terminate the
|
||||||
|
licenses of parties who have received copies or rights from you under
|
||||||
|
this License. If your rights have been terminated and not permanently
|
||||||
|
reinstated, you do not qualify to receive new licenses for the same
|
||||||
|
material under section 10.
|
||||||
|
|
||||||
|
9. Acceptance Not Required for Having Copies.
|
||||||
|
|
||||||
|
You are not required to accept this License in order to receive or
|
||||||
|
run a copy of the Program. Ancillary propagation of a covered work
|
||||||
|
occurring solely as a consequence of using peer-to-peer transmission
|
||||||
|
to receive a copy likewise does not require acceptance. However,
|
||||||
|
nothing other than this License grants you permission to propagate or
|
||||||
|
modify any covered work. These actions infringe copyright if you do
|
||||||
|
not accept this License. Therefore, by modifying or propagating a
|
||||||
|
covered work, you indicate your acceptance of this License to do so.
|
||||||
|
|
||||||
|
10. Automatic Licensing of Downstream Recipients.
|
||||||
|
|
||||||
|
Each time you convey a covered work, the recipient automatically
|
||||||
|
receives a license from the original licensors, to run, modify and
|
||||||
|
propagate that work, subject to this License. You are not responsible
|
||||||
|
for enforcing compliance by third parties with this License.
|
||||||
|
|
||||||
|
An "entity transaction" is a transaction transferring control of an
|
||||||
|
organization, or substantially all assets of one, or subdividing an
|
||||||
|
organization, or merging organizations. If propagation of a covered
|
||||||
|
work results from an entity transaction, each party to that
|
||||||
|
transaction who receives a copy of the work also receives whatever
|
||||||
|
licenses to the work the party's predecessor in interest had or could
|
||||||
|
give under the previous paragraph, plus a right to possession of the
|
||||||
|
Corresponding Source of the work from the predecessor in interest, if
|
||||||
|
the predecessor has it or can get it with reasonable efforts.
|
||||||
|
|
||||||
|
You may not impose any further restrictions on the exercise of the
|
||||||
|
rights granted or affirmed under this License. For example, you may
|
||||||
|
not impose a license fee, royalty, or other charge for exercise of
|
||||||
|
rights granted under this License, and you may not initiate litigation
|
||||||
|
(including a cross-claim or counterclaim in a lawsuit) alleging that
|
||||||
|
any patent claim is infringed by making, using, selling, offering for
|
||||||
|
sale, or importing the Program or any portion of it.
|
||||||
|
|
||||||
|
11. Patents.
|
||||||
|
|
||||||
|
A "contributor" is a copyright holder who authorizes use under this
|
||||||
|
License of the Program or a work on which the Program is based. The
|
||||||
|
work thus licensed is called the contributor's "contributor version".
|
||||||
|
|
||||||
|
A contributor's "essential patent claims" are all patent claims
|
||||||
|
owned or controlled by the contributor, whether already acquired or
|
||||||
|
hereafter acquired, that would be infringed by some manner, permitted
|
||||||
|
by this License, of making, using, or selling its contributor version,
|
||||||
|
but do not include claims that would be infringed only as a
|
||||||
|
consequence of further modification of the contributor version. For
|
||||||
|
purposes of this definition, "control" includes the right to grant
|
||||||
|
patent sublicenses in a manner consistent with the requirements of
|
||||||
|
this License.
|
||||||
|
|
||||||
|
Each contributor grants you a non-exclusive, worldwide, royalty-free
|
||||||
|
patent license under the contributor's essential patent claims, to
|
||||||
|
make, use, sell, offer for sale, import and otherwise run, modify and
|
||||||
|
propagate the contents of its contributor version.
|
||||||
|
|
||||||
|
In the following three paragraphs, a "patent license" is any express
|
||||||
|
agreement or commitment, however denominated, not to enforce a patent
|
||||||
|
(such as an express permission to practice a patent or covenant not to
|
||||||
|
sue for patent infringement). To "grant" such a patent license to a
|
||||||
|
party means to make such an agreement or commitment not to enforce a
|
||||||
|
patent against the party.
|
||||||
|
|
||||||
|
If you convey a covered work, knowingly relying on a patent license,
|
||||||
|
and the Corresponding Source of the work is not available for anyone
|
||||||
|
to copy, free of charge and under the terms of this License, through a
|
||||||
|
publicly available network server or other readily accessible means,
|
||||||
|
then you must either (1) cause the Corresponding Source to be so
|
||||||
|
available, or (2) arrange to deprive yourself of the benefit of the
|
||||||
|
patent license for this particular work, or (3) arrange, in a manner
|
||||||
|
consistent with the requirements of this License, to extend the patent
|
||||||
|
license to downstream recipients. "Knowingly relying" means you have
|
||||||
|
actual knowledge that, but for the patent license, your conveying the
|
||||||
|
covered work in a country, or your recipient's use of the covered work
|
||||||
|
in a country, would infringe one or more identifiable patents in that
|
||||||
|
country that you have reason to believe are valid.
|
||||||
|
|
||||||
|
If, pursuant to or in connection with a single transaction or
|
||||||
|
arrangement, you convey, or propagate by procuring conveyance of, a
|
||||||
|
covered work, and grant a patent license to some of the parties
|
||||||
|
receiving the covered work authorizing them to use, propagate, modify
|
||||||
|
or convey a specific copy of the covered work, then the patent license
|
||||||
|
you grant is automatically extended to all recipients of the covered
|
||||||
|
work and works based on it.
|
||||||
|
|
||||||
|
A patent license is "discriminatory" if it does not include within
|
||||||
|
the scope of its coverage, prohibits the exercise of, or is
|
||||||
|
conditioned on the non-exercise of one or more of the rights that are
|
||||||
|
specifically granted under this License. You may not convey a covered
|
||||||
|
work if you are a party to an arrangement with a third party that is
|
||||||
|
in the business of distributing software, under which you make payment
|
||||||
|
to the third party based on the extent of your activity of conveying
|
||||||
|
the work, and under which the third party grants, to any of the
|
||||||
|
parties who would receive the covered work from you, a discriminatory
|
||||||
|
patent license (a) in connection with copies of the covered work
|
||||||
|
conveyed by you (or copies made from those copies), or (b) primarily
|
||||||
|
for and in connection with specific products or compilations that
|
||||||
|
contain the covered work, unless you entered into that arrangement,
|
||||||
|
or that patent license was granted, prior to 28 March 2007.
|
||||||
|
|
||||||
|
Nothing in this License shall be construed as excluding or limiting
|
||||||
|
any implied license or other defenses to infringement that may
|
||||||
|
otherwise be available to you under applicable patent law.
|
||||||
|
|
||||||
|
12. No Surrender of Others' Freedom.
|
||||||
|
|
||||||
|
If conditions are imposed on you (whether by court order, agreement or
|
||||||
|
otherwise) that contradict the conditions of this License, they do not
|
||||||
|
excuse you from the conditions of this License. If you cannot convey a
|
||||||
|
covered work so as to satisfy simultaneously your obligations under this
|
||||||
|
License and any other pertinent obligations, then as a consequence you may
|
||||||
|
not convey it at all. For example, if you agree to terms that obligate you
|
||||||
|
to collect a royalty for further conveying from those to whom you convey
|
||||||
|
the Program, the only way you could satisfy both those terms and this
|
||||||
|
License would be to refrain entirely from conveying the Program.
|
||||||
|
|
||||||
|
13. Use with the GNU Affero General Public License.
|
||||||
|
|
||||||
|
Notwithstanding any other provision of this License, you have
|
||||||
|
permission to link or combine any covered work with a work licensed
|
||||||
|
under version 3 of the GNU Affero General Public License into a single
|
||||||
|
combined work, and to convey the resulting work. The terms of this
|
||||||
|
License will continue to apply to the part which is the covered work,
|
||||||
|
but the special requirements of the GNU Affero General Public License,
|
||||||
|
section 13, concerning interaction through a network will apply to the
|
||||||
|
combination as such.
|
||||||
|
|
||||||
|
14. Revised Versions of this License.
|
||||||
|
|
||||||
|
The Free Software Foundation may publish revised and/or new versions of
|
||||||
|
the GNU General Public License from time to time. Such new versions will
|
||||||
|
be similar in spirit to the present version, but may differ in detail to
|
||||||
|
address new problems or concerns.
|
||||||
|
|
||||||
|
Each version is given a distinguishing version number. If the
|
||||||
|
Program specifies that a certain numbered version of the GNU General
|
||||||
|
Public License "or any later version" applies to it, you have the
|
||||||
|
option of following the terms and conditions either of that numbered
|
||||||
|
version or of any later version published by the Free Software
|
||||||
|
Foundation. If the Program does not specify a version number of the
|
||||||
|
GNU General Public License, you may choose any version ever published
|
||||||
|
by the Free Software Foundation.
|
||||||
|
|
||||||
|
If the Program specifies that a proxy can decide which future
|
||||||
|
versions of the GNU General Public License can be used, that proxy's
|
||||||
|
public statement of acceptance of a version permanently authorizes you
|
||||||
|
to choose that version for the Program.
|
||||||
|
|
||||||
|
Later license versions may give you additional or different
|
||||||
|
permissions. However, no additional obligations are imposed on any
|
||||||
|
author or copyright holder as a result of your choosing to follow a
|
||||||
|
later version.
|
||||||
|
|
||||||
|
15. Disclaimer of Warranty.
|
||||||
|
|
||||||
|
THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY
|
||||||
|
APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT
|
||||||
|
HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY
|
||||||
|
OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO,
|
||||||
|
THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||||
|
PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM
|
||||||
|
IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF
|
||||||
|
ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
|
||||||
|
|
||||||
|
16. Limitation of Liability.
|
||||||
|
|
||||||
|
IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
||||||
|
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS
|
||||||
|
THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY
|
||||||
|
GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE
|
||||||
|
USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF
|
||||||
|
DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD
|
||||||
|
PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS),
|
||||||
|
EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF
|
||||||
|
SUCH DAMAGES.
|
||||||
|
|
||||||
|
17. Interpretation of Sections 15 and 16.
|
||||||
|
|
||||||
|
If the disclaimer of warranty and limitation of liability provided
|
||||||
|
above cannot be given local legal effect according to their terms,
|
||||||
|
reviewing courts shall apply local law that most closely approximates
|
||||||
|
an absolute waiver of all civil liability in connection with the
|
||||||
|
Program, unless a warranty or assumption of liability accompanies a
|
||||||
|
copy of the Program in return for a fee.
|
||||||
|
|
||||||
|
END OF TERMS AND CONDITIONS
|
||||||
|
|
||||||
|
How to Apply These Terms to Your New Programs
|
||||||
|
|
||||||
|
If you develop a new program, and you want it to be of the greatest
|
||||||
|
possible use to the public, the best way to achieve this is to make it
|
||||||
|
free software which everyone can redistribute and change under these terms.
|
||||||
|
|
||||||
|
To do so, attach the following notices to the program. It is safest
|
||||||
|
to attach them to the start of each source file to most effectively
|
||||||
|
state the exclusion of warranty; and each file should have at least
|
||||||
|
the "copyright" line and a pointer to where the full notice is found.
|
||||||
|
|
||||||
|
<one line to give the program's name and a brief idea of what it does.>
|
||||||
|
Copyright (C) <year> <name of author>
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
Also add information on how to contact you by electronic and paper mail.
|
||||||
|
|
||||||
|
If the program does terminal interaction, make it output a short
|
||||||
|
notice like this when it starts in an interactive mode:
|
||||||
|
|
||||||
|
<program> Copyright (C) <year> <name of author>
|
||||||
|
This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
||||||
|
This is free software, and you are welcome to redistribute it
|
||||||
|
under certain conditions; type `show c' for details.
|
||||||
|
|
||||||
|
The hypothetical commands `show w' and `show c' should show the appropriate
|
||||||
|
parts of the General Public License. Of course, your program's commands
|
||||||
|
might be different; for a GUI interface, you would use an "about box".
|
||||||
|
|
||||||
|
You should also get your employer (if you work as a programmer) or school,
|
||||||
|
if any, to sign a "copyright disclaimer" for the program, if necessary.
|
||||||
|
For more information on this, and how to apply and follow the GNU GPL, see
|
||||||
|
<http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
The GNU General Public License does not permit incorporating your program
|
||||||
|
into proprietary programs. If your program is a subroutine library, you
|
||||||
|
may consider it more useful to permit linking proprietary applications with
|
||||||
|
the library. If this is what you want to do, use the GNU Lesser General
|
||||||
|
Public License instead of this License. But first, please read
|
||||||
|
<http://www.gnu.org/philosophy/why-not-lgpl.html>.
|
||||||
298
gource/ChangeLog.txt
Normal file
298
gource/ChangeLog.txt
Normal file
@@ -0,0 +1,298 @@
|
|||||||
|
0.51:
|
||||||
|
* Fixed --font-file relative path handling.
|
||||||
|
* Fixed a bug in resolving the repository root directory from a relative path.
|
||||||
|
|
||||||
|
0.50:
|
||||||
|
* Right mouse button rotation now pivots around the camera.
|
||||||
|
* Added --font-file option.
|
||||||
|
* Added --enable-font-file option to configure.
|
||||||
|
* Added --no-time-travel option (Lars Schmertmann).
|
||||||
|
* Added --dir-name-position option (Lars Schmertmann).
|
||||||
|
* Added --file-extension-fallback option (Lars Schmertmann).
|
||||||
|
* Added --user-show-filter option (Victor Lopez).
|
||||||
|
* Added --disable-input option (Joey Parrish).
|
||||||
|
* Added --loop-delay-seconds option (Joey Parrish).
|
||||||
|
* Added --font-scale option.
|
||||||
|
* Added filename, dirname and user font size options (Carl Colena).
|
||||||
|
* Added workaround for FFMpeg error parsing Gource PPM video output.
|
||||||
|
* Fixed a bug in the Mercurial log parser that caused changes to be missed.
|
||||||
|
* Fixed file removal being cancelled by an action with an earlier timestamp.
|
||||||
|
* Fixed a bug in the log file format detection that could result in the wrong
|
||||||
|
first entry being displayed for a custom log.
|
||||||
|
* Fixed a bug where automatically cycling through a config with multiple
|
||||||
|
repositories reset settings to their defaults.
|
||||||
|
|
||||||
|
0.49:
|
||||||
|
* Fixed compatibility with GLM 0.9.9.0.
|
||||||
|
|
||||||
|
0.48:
|
||||||
|
* Can now generate logs from git sub module directories.
|
||||||
|
|
||||||
|
0.47:
|
||||||
|
* Fixed low mouse movement speed with some mice while repositioning camera.
|
||||||
|
|
||||||
|
0.46:
|
||||||
|
* Added --screen option.
|
||||||
|
|
||||||
|
0.45:
|
||||||
|
* Added --window-position XxY option.
|
||||||
|
* Added --frameless option.
|
||||||
|
* Added --file-show-filter REGEX option (swoogles).
|
||||||
|
* Added --filename-time and filename-colour options (gh2k).
|
||||||
|
* Improved handling of very low seconds-per-day values (malengrin).
|
||||||
|
* Fixed crash when SVN log lacks author information (obarthel).
|
||||||
|
* Additional git log command validation (cym13).
|
||||||
|
* Allow lower case hex colours in custom logs (HSorensen).
|
||||||
|
* Enabled STDOUT support with --output-stream '-' on Windows (circulosmeos).
|
||||||
|
* Now requires SDL 2 to build (deprecated SDL 1.2 support removed).
|
||||||
|
|
||||||
|
0.44:
|
||||||
|
* Fixed crash when taking a screenshot with an odd resolution.
|
||||||
|
* Fixed type deduction compilation error with newer versions of GCC.
|
||||||
|
* Documentation improvements.
|
||||||
|
|
||||||
|
0.43:
|
||||||
|
* Updated boost autoconf macros to fix multi-arch detection.
|
||||||
|
|
||||||
|
0.42:
|
||||||
|
* Fixed bzr log command when no start date was specified (chrisf).
|
||||||
|
* Fixed hg log commit order when date range specified.
|
||||||
|
* Fixed hg log command line on Windows.
|
||||||
|
* Fixed parser bug in date range filtering code.
|
||||||
|
|
||||||
|
0.41:
|
||||||
|
* Multi-monitor support using SDL 2.0 when available.
|
||||||
|
* SDL 1.2 support is deprecated.
|
||||||
|
* Full screen mode now uses desktop resolution by default.
|
||||||
|
* Added --start-date, --stop-date 'YYYY-MM-DD hh:mm:ss' options.
|
||||||
|
* Added --dir-name-depth option.
|
||||||
|
* Changed --file-idle-time default value to 0.
|
||||||
|
* Changed screenshot format to PNG.
|
||||||
|
|
||||||
|
0.40:
|
||||||
|
* Added caption support.
|
||||||
|
* Improved command line interoperability on Windows.
|
||||||
|
* Fixed directory deletion short circuiting processing the rest of a commit.
|
||||||
|
* Fixed issue loading non-ascii user image filenames on windows.
|
||||||
|
* Ignore UTF-8 byte order mark at the start of lines in custom log files.
|
||||||
|
* Fix to boost macros for Macs and non-GNU systems (mistydemeo).
|
||||||
|
* Autotools improvements (flameeyes).
|
||||||
|
|
||||||
|
0.39:
|
||||||
|
* Fixed blurry non power of 2 logos.
|
||||||
|
* File colour changes now supported in custom logs (rmyorston).
|
||||||
|
* Fixed building against Boost 1.50 (svenstaro).
|
||||||
|
* Updated boost autoconf macros (flameeyes).
|
||||||
|
* Autogen script (matthiaskrgr).
|
||||||
|
|
||||||
|
0.38:
|
||||||
|
* New high quality sprites.
|
||||||
|
* Fullscreen toggle with alt + enter.
|
||||||
|
* Window is now resizable. -WIDTHxHEIGHT! creates a non-resizable window.
|
||||||
|
* Lowered minimum zoom distance.
|
||||||
|
* Use AM_CPPFLAGS in Makefile.am to allow passing custom CPPFLAGS.
|
||||||
|
* Don't add files that match the path of a known directory.
|
||||||
|
* Fixed divide by zero in text shader causing artifacts on some video cards.
|
||||||
|
* Recursively search for repository directory when log-format not specified
|
||||||
|
(thanks to Jörg Bachmann for original concept / prototype).
|
||||||
|
* New dependency on Boost Filesystem.
|
||||||
|
* Doubled the maximum zoom out distance.
|
||||||
|
* Allow negative timestamps before 1970 in custom log (artzub).
|
||||||
|
* Fix for UTF8-CPP checked.h compilation issue (vszakats).
|
||||||
|
* Fixed bug causing missing characters in text.
|
||||||
|
* Fixed --highlight-users option not using highlight-colour.
|
||||||
|
* highlight-colour default changed to white.
|
||||||
|
* Added --selection-colour option (applied to selected users and files).
|
||||||
|
* Added --dir-colour option (applied to directories).
|
||||||
|
|
||||||
|
0.37:
|
||||||
|
* Made SVN log GMT timestamp conversion fix portable.
|
||||||
|
|
||||||
|
0.36:
|
||||||
|
* Fixed SVN log GMT timestamp conversion.
|
||||||
|
* Fixed issue with sub-dirs of deleted dir not being removed in some cases.
|
||||||
|
|
||||||
|
0.35:
|
||||||
|
* Added long file extension truncation handling to file key (--key).
|
||||||
|
* Treat changes in Mercurial log files with the same time/user as one commit.
|
||||||
|
* Fixed handling of spaces in directory names with Mercurial.
|
||||||
|
* Fixed --font-colour option.
|
||||||
|
|
||||||
|
0.34:
|
||||||
|
* Now using VBOs and shaders for faster rendering when OpenGL 2.0 is available.
|
||||||
|
* Eliminated bloom colour banding artifacts (requires OpenGL 2.0).
|
||||||
|
* New font rendering library derived from FTGL (FTGL no longer required).
|
||||||
|
* Single pass font/shadow rendering (with lots of help from Chris Forbes).
|
||||||
|
* Added --no-vsync option.
|
||||||
|
* Fixed bug where tree is out of alignment with object positions in windowed
|
||||||
|
mode due to using the wrong display dimensions internally.
|
||||||
|
* Removed default max-files limit.
|
||||||
|
|
||||||
|
0.33:
|
||||||
|
* Added --hide root option to not draw branches from the root directory.
|
||||||
|
* Fixed log parsing of Bazaar merges and tagged commits.
|
||||||
|
* --output-custom-log now skips unparsed log entries instead of exiting.
|
||||||
|
|
||||||
|
0.32:
|
||||||
|
* Fixed behaviour of user camera tracking.
|
||||||
|
|
||||||
|
0.31:
|
||||||
|
* Added --with-tinyxml option to configure (use the system TinyXML library).
|
||||||
|
|
||||||
|
0.30:
|
||||||
|
* Fixed crash when SVN log entry contains no 'paths' element.
|
||||||
|
* Handle directory deletion (happens in SVN logs).
|
||||||
|
|
||||||
|
0.29:
|
||||||
|
* SVN built-in support.
|
||||||
|
* cvs2cl log support (cvs-exp support is now deprecated).
|
||||||
|
* Made camera behaviour when zooming and selecting objects more intuitive.
|
||||||
|
* Improved interactive performance.
|
||||||
|
* Added file extension key (--key or toggled with 'K').
|
||||||
|
* Added mouse-over tool tips.
|
||||||
|
* Added --highlight-colour option.
|
||||||
|
* Added --hash-seed option. The S key now randomizes colours.
|
||||||
|
* Added --output-custom-log option.
|
||||||
|
* Exposed --time-scale option (previously only available interactively).
|
||||||
|
* Removed arbitrary 1024 maximum length limit for log lines.
|
||||||
|
* Fixed two file colouring bugs (quoted files from git, period in file path).
|
||||||
|
* Fix handling of avatars for UTF-8 usernames on MACOSX (Christian Köstlin).
|
||||||
|
* Recover from video mode failing to set due to multi-sampling (Siddhesh Poyarekar).
|
||||||
|
|
||||||
|
0.28:
|
||||||
|
* Bazaar support for merged commits (Nick Moffit).
|
||||||
|
* C++ efficiency improvements (Oliver Smith).
|
||||||
|
* Improved cvs-exp log compatibility.
|
||||||
|
* Re-show name of user when adding a new action if user is idle.
|
||||||
|
* Added --padding option to control camera view padding.
|
||||||
|
* More accurate camera tracking (tracks the bounding boxes of objects).
|
||||||
|
* Improved automatic rotation logic.
|
||||||
|
|
||||||
|
0.27:
|
||||||
|
* Display time stops at the time of the last commit.
|
||||||
|
* Users fade out when end reached rather than ending abruptly.
|
||||||
|
* Position slider is now hidden by default if recording a video.
|
||||||
|
* Automatic camera rotation for better use of screen space.
|
||||||
|
* Support international keyboards (Peter Kjellerstedt).
|
||||||
|
* C++ efficiency improvements (Jacob Metcalfe).
|
||||||
|
* Fixed crash when reading from STDIN.
|
||||||
|
* Fixed intermittent crash closing Gource when using --output-ppm-stream.
|
||||||
|
* Added ini style config file support (see --load/save-config).
|
||||||
|
* Added screenshot button (F12). Screenshots respect the alpha channel.
|
||||||
|
* Added --transparent to make the background see-through (for screenshots).
|
||||||
|
* Added --logo and --background-image options.
|
||||||
|
* Added --dont-stop option for manual exiting when recording videos.
|
||||||
|
* Added --stop-at-time option to stop Gource after a number of seconds.
|
||||||
|
* Added --hide 'mouse' option.
|
||||||
|
* Added --highlight-dirs option.
|
||||||
|
* Added --file-extensions to show filename extensions only.
|
||||||
|
* Added --user-filter REGEX option.
|
||||||
|
* Allow --file-idle-time 0 (files will never expire).
|
||||||
|
* Allow --start-position 'random' to set a random start position.
|
||||||
|
* --log-command VCS replaces multiple --log-command-VCS options.
|
||||||
|
* Replaced --disable-progress and --disable-bloom with arguments to --hide.
|
||||||
|
|
||||||
|
0.26a:
|
||||||
|
* Updated to latest version of GL autoconf macros.
|
||||||
|
|
||||||
|
0.26:
|
||||||
|
* Improved mouse dragging.
|
||||||
|
* Holding right mouse button and moving the mouse rotates the view.
|
||||||
|
* The middle mouse button now toggles the camera mode.
|
||||||
|
* Username positions now scale correctly.
|
||||||
|
* Simulation time no longer incremented while paused, counting towards file time lag.
|
||||||
|
* M key now toggles mouse visibility.
|
||||||
|
* Added --hide option to use instead of multiple --hide-ELEMENT options.
|
||||||
|
|
||||||
|
0.25:
|
||||||
|
* Bazaar support (John Arbash Meinel).
|
||||||
|
* Dragging the mouse on the background moves the camera.
|
||||||
|
* Added --camera-mode option (track,overview).
|
||||||
|
* Support DOS line endings in logs.
|
||||||
|
* Improved compatibility of hg log command (Brendan Cully).
|
||||||
|
* Fixed PPM exporter producing blank images on some video cards.
|
||||||
|
* Fixed parsing of negative timezones from cvs-exp.pl logs.
|
||||||
|
* Fixed various gdb and compiler warnings.
|
||||||
|
|
||||||
|
0.24:
|
||||||
|
* PPM output speed improvements, including using a second thread (HighlandSun).
|
||||||
|
* Now using standard autotools (Flameeyes).
|
||||||
|
* Fixed --max-file-lag not working with some custom log files.
|
||||||
|
* Gource will stop at the end of the log by default when recording a video.
|
||||||
|
* Fixed STDIN stopping working after the first lot of records with tail -f.
|
||||||
|
* Added proper exception handling.
|
||||||
|
* Print errors to stderr.
|
||||||
|
|
||||||
|
0.23:
|
||||||
|
* Hiding filenames no longer hides directory names.
|
||||||
|
* Fixed --stop-on-idle option.
|
||||||
|
* Added --stop-at-end option (more intuitive than --stop-position 1.0).
|
||||||
|
|
||||||
|
0.22:
|
||||||
|
* Fixed Mercurial log order.
|
||||||
|
|
||||||
|
0.21b:
|
||||||
|
* Fixed windows build.
|
||||||
|
|
||||||
|
0.21:
|
||||||
|
* Some documentation fixes.
|
||||||
|
|
||||||
|
0.20:
|
||||||
|
* Added bloom effect (turn off with --disable-bloom).
|
||||||
|
* Added support for Mercurial (thanks to Justin Love for gource.style).
|
||||||
|
* --start-position option now works in combination with --disable-progress.
|
||||||
|
|
||||||
|
0.19:
|
||||||
|
* Use time_t instead of long for timestamps.
|
||||||
|
|
||||||
|
0.18:
|
||||||
|
* Fixed camera movement while the simulation is paused.
|
||||||
|
|
||||||
|
0.17:
|
||||||
|
* Show correct month for CVS logs.
|
||||||
|
* Added time scaling (Bitshifter).
|
||||||
|
|
||||||
|
0.16:
|
||||||
|
* Added --hide-dirnames option.
|
||||||
|
* Added --user-scale option.
|
||||||
|
* Added --date-format option (Pat Notz).
|
||||||
|
* Fix bug when encountering long log lines.
|
||||||
|
* Fixed incorrect parsing of trivial merges.
|
||||||
|
* Fixed building issues on OSX.
|
||||||
|
|
||||||
|
0.15:
|
||||||
|
* Added PPM output support for creating videos (Johannes Schindelin).
|
||||||
|
* Added experimental Apache combined access log support (--log-format apache).
|
||||||
|
* Added --stop-position and --stop-on-idle options (useful for making videos).
|
||||||
|
* Added --max-file-lag option to limit how long after a commit file changes can take to appear.
|
||||||
|
* Added --no-renames to the git log command as they don't display correctly.
|
||||||
|
* Added --max-user-speed and --user-friction as options.
|
||||||
|
* Now builds on OSX Leopard (with the required libaries installed).
|
||||||
|
* Caught raw exception from replace_invalid().
|
||||||
|
* Added CXXFLAGS. You may want to override the default (eg CXXFLAGS=-O3 ./configure).
|
||||||
|
|
||||||
|
0.14:
|
||||||
|
* Updated SVN instructions.
|
||||||
|
|
||||||
|
0.13:
|
||||||
|
* Removed single quotes from log command (fixes running gource --git-log-command in back ticks)
|
||||||
|
* Added SVN instructions.
|
||||||
|
* Fixed manpage hyphens.
|
||||||
|
|
||||||
|
0.12:
|
||||||
|
* Added --enable-ttf-font-dir=DIR option to configure (to specify the ttf-freefont directory).
|
||||||
|
* UTF-8 support using UTF8-CPP (http://utfcpp.sourceforge.net/).
|
||||||
|
* Changed the git log command (see --git-log-command) to require less work to parse.
|
||||||
|
Log files generated with the previous git-log command used by gource should continue to work.
|
||||||
|
* Allow --seconds-per-day value less than 1.0.
|
||||||
|
* Added --git-branch command.
|
||||||
|
* Added --loop command.
|
||||||
|
* Added --crop command.
|
||||||
|
|
||||||
|
0.11:
|
||||||
|
* Made N key skip to next entry.
|
||||||
|
* Documented --user-image-dir flag.
|
||||||
|
* temp file name now uses uid instead of time
|
||||||
|
|
||||||
|
0.1:
|
||||||
|
* First release.
|
||||||
469
gource/README.txt
Normal file
469
gource/README.txt
Normal file
@@ -0,0 +1,469 @@
|
|||||||
|
|
||||||
|
Gource
|
||||||
|
|
||||||
|
software version control visualization
|
||||||
|
|
||||||
|
Copyright (C) 2009 Andrew Caudwell
|
||||||
|
|
||||||
|
http://gource.io
|
||||||
|
|
||||||
|
Contents
|
||||||
|
========
|
||||||
|
|
||||||
|
1. Description
|
||||||
|
2. Requirements
|
||||||
|
3. Using Gource
|
||||||
|
4. Copyright
|
||||||
|
|
||||||
|
1. Description
|
||||||
|
==============
|
||||||
|
|
||||||
|
OpenGL-based 3D visualisation tool for source control repositories.
|
||||||
|
|
||||||
|
The repository is displayed as a tree where the root of the repository is the
|
||||||
|
centre, directories are branches and files are leaves. Contributors to the
|
||||||
|
source code appear and disappear as they contribute to specific files and
|
||||||
|
directories.
|
||||||
|
|
||||||
|
2. Requirements
|
||||||
|
===============
|
||||||
|
|
||||||
|
Gource's display is rendered using OpenGL and requires a 3D accelerated video
|
||||||
|
card to run.
|
||||||
|
|
||||||
|
3. Using Gource
|
||||||
|
===============
|
||||||
|
|
||||||
|
gource [options] [path]
|
||||||
|
|
||||||
|
options:
|
||||||
|
|
||||||
|
-h, --help
|
||||||
|
Help ('-H' for extended help).
|
||||||
|
|
||||||
|
-WIDTHxHEIGHT, --viewport WIDTHxHEIGHT
|
||||||
|
Set the viewport size. If -f is also supplied, will attempt to set
|
||||||
|
the video mode to this also. Add ! to make the window non-resizable.
|
||||||
|
|
||||||
|
--screen SCREEN
|
||||||
|
Set the number of the screen to display on.
|
||||||
|
|
||||||
|
--window-position XxY
|
||||||
|
Initial window position on your desktop which may be made up of
|
||||||
|
multiple monitors.
|
||||||
|
|
||||||
|
This will override the screen setting so don't specify both.
|
||||||
|
|
||||||
|
--frameless
|
||||||
|
Frameless window.
|
||||||
|
|
||||||
|
-f, --fullscreen
|
||||||
|
Fullscreen.
|
||||||
|
|
||||||
|
-w, --windowed
|
||||||
|
Windowed.
|
||||||
|
|
||||||
|
--transparent
|
||||||
|
Make the background transparent. Only really useful for screenshots.
|
||||||
|
|
||||||
|
--start-date "YYYY-MM-DD hh:mm:ss +tz"
|
||||||
|
Start with the first entry after the supplied date and optional time.
|
||||||
|
|
||||||
|
If a time zone offset isn't specified the local time zone is used.
|
||||||
|
|
||||||
|
Example accepted formats:
|
||||||
|
|
||||||
|
"2012-06-30"
|
||||||
|
"2012-06-30 12:00"
|
||||||
|
"2012-06-30 12:00:00 +12"
|
||||||
|
|
||||||
|
--stop-date "YYYY-MM-DD hh:mm:ss +tz"
|
||||||
|
Stop after the last entry prior to the supplied date and optional time.
|
||||||
|
|
||||||
|
Uses the same format as --start-date.
|
||||||
|
|
||||||
|
-p, --start-position POSITION
|
||||||
|
Begin at some position in the log (between 0.0 and 1.0 or 'random').
|
||||||
|
|
||||||
|
--stop-position POSITION
|
||||||
|
Stop (exit) at some position in the log (does not work with STDIN).
|
||||||
|
|
||||||
|
-t, --stop-at-time SECONDS
|
||||||
|
Stop (exit) after a specified number of seconds.
|
||||||
|
|
||||||
|
--stop-at-end
|
||||||
|
Stop (exit) at the end of the log / stream.
|
||||||
|
|
||||||
|
--loop
|
||||||
|
Loop back to the start of the log when the end is reached.
|
||||||
|
|
||||||
|
--loop-delay-seconds
|
||||||
|
Seconds to delay before looping.
|
||||||
|
|
||||||
|
-a, --auto-skip-seconds SECONDS
|
||||||
|
Skip to next entry if nothing happens for a number of seconds.
|
||||||
|
|
||||||
|
-s, --seconds-per-day SECONDS
|
||||||
|
Speed of simulation in seconds per day.
|
||||||
|
|
||||||
|
--realtime
|
||||||
|
Realtime playback speed.
|
||||||
|
|
||||||
|
--no-time-travel
|
||||||
|
Use the time of the last commit if the time of a commit is in the past.
|
||||||
|
|
||||||
|
-c, --time-scale SCALE
|
||||||
|
Change simulation time scale.
|
||||||
|
|
||||||
|
-i, --file-idle-time SECONDS
|
||||||
|
Time in seconds files remain idle before they are removed or 0
|
||||||
|
for no limit.
|
||||||
|
|
||||||
|
-e, --elasticity FLOAT
|
||||||
|
Elasticity of nodes.
|
||||||
|
|
||||||
|
-b, --background-colour FFFFFF
|
||||||
|
Background colour in hex.
|
||||||
|
|
||||||
|
--background-image IMAGE
|
||||||
|
Set a background image.
|
||||||
|
|
||||||
|
--logo IMAGE
|
||||||
|
Logo to display in the foreground.
|
||||||
|
|
||||||
|
--logo-offset XxY
|
||||||
|
Offset position of the logo.
|
||||||
|
|
||||||
|
--title TITLE
|
||||||
|
Set a title.
|
||||||
|
|
||||||
|
--font-file FILE
|
||||||
|
Specify the font. Should work with most font file formats supported by FreeType, such as TTF and OTF, among others.
|
||||||
|
|
||||||
|
--font-scale SCALE
|
||||||
|
Scale the size of all fonts.
|
||||||
|
|
||||||
|
--font-size SIZE
|
||||||
|
Font size used by the date and title.
|
||||||
|
|
||||||
|
--file-font-size SIZE
|
||||||
|
Font size of filenames.
|
||||||
|
|
||||||
|
--dir-font-size SIZE
|
||||||
|
Font size of directory names
|
||||||
|
|
||||||
|
--user-font-size SIZE
|
||||||
|
Font size of user names.
|
||||||
|
|
||||||
|
--font-colour FFFFFF
|
||||||
|
Font colour used by the date and title in hex.
|
||||||
|
|
||||||
|
--key
|
||||||
|
Show file extension key.
|
||||||
|
|
||||||
|
--date-format FORMAT
|
||||||
|
Specify display date string (strftime format).
|
||||||
|
|
||||||
|
--log-command VCS
|
||||||
|
Show the VCS log command used by gource (git,svn,hg,bzr,cvs2cl).
|
||||||
|
|
||||||
|
--log-format VCS
|
||||||
|
Specify the log format (git,svn,hg,bzr,cvs2cl,custom).
|
||||||
|
|
||||||
|
Required when reading from STDIN.
|
||||||
|
|
||||||
|
--git-branch
|
||||||
|
Get the git log of a branch other than the current one.
|
||||||
|
|
||||||
|
--follow-user USER
|
||||||
|
Have the camera automatically follow a particular user.
|
||||||
|
|
||||||
|
--highlight-dirs
|
||||||
|
Highlight the names of all directories.
|
||||||
|
|
||||||
|
--highlight-user USER
|
||||||
|
Highlight the names of a particular user.
|
||||||
|
|
||||||
|
--highlight-users
|
||||||
|
Highlight the names of all users.
|
||||||
|
|
||||||
|
--highlight-colour FFFFFF
|
||||||
|
Font colour for highlighted users in hex.
|
||||||
|
|
||||||
|
--selection-colour FFFFFF
|
||||||
|
Font colour for selected users and files.
|
||||||
|
|
||||||
|
--filename-colour FFFFFF
|
||||||
|
Font colour for filenames.
|
||||||
|
|
||||||
|
--dir-colour FFFFFF
|
||||||
|
Font colour for directories.
|
||||||
|
|
||||||
|
--dir-name-depth DEPTH
|
||||||
|
Draw names of directories down to a specific depth in the tree.
|
||||||
|
|
||||||
|
--dir-name-position FLOAT
|
||||||
|
Position along edge of the directory name
|
||||||
|
(between 0.1 and 1.0, default is 0.5).
|
||||||
|
|
||||||
|
--filename-time SECONDS
|
||||||
|
Duration to keep filenames on screen (>= 2.0).
|
||||||
|
|
||||||
|
--file-extensions
|
||||||
|
Show filename extensions only.
|
||||||
|
|
||||||
|
--file-extension-fallback
|
||||||
|
Use filename as extension if the extension is missing or empty.
|
||||||
|
|
||||||
|
--file-filter REGEX
|
||||||
|
Filter out file paths matching the specified regular expression.
|
||||||
|
|
||||||
|
--file-show-filter REGEX
|
||||||
|
Show only file paths matching the specified regular expression.
|
||||||
|
|
||||||
|
--user-filter REGEX
|
||||||
|
Filter usernames matching the specified regular expression.
|
||||||
|
|
||||||
|
--user-show-filter REGEX
|
||||||
|
Show only usernames matching the specified regular expression.
|
||||||
|
|
||||||
|
--user-image-dir DIRECTORY
|
||||||
|
Directory containing .jpg or .png images of users
|
||||||
|
(eg "Full Name.png") to use as avatars.
|
||||||
|
|
||||||
|
--default-user-image IMAGE
|
||||||
|
Path of .jpg or .png to use as the default user image.
|
||||||
|
|
||||||
|
--colour-images
|
||||||
|
Colourize user images.
|
||||||
|
|
||||||
|
--crop AXIS
|
||||||
|
Crop view on an axis (vertical,horizontal).
|
||||||
|
|
||||||
|
--padding FLOAT
|
||||||
|
Camera view padding.
|
||||||
|
|
||||||
|
--multi-sampling
|
||||||
|
Enable multi-sampling.
|
||||||
|
|
||||||
|
--no-vsync
|
||||||
|
Disable vsync.
|
||||||
|
|
||||||
|
--bloom-multiplier FLOAT
|
||||||
|
Adjust the amount of bloom.
|
||||||
|
|
||||||
|
--bloom-intensity FLOAT
|
||||||
|
Adjust the intensity of the bloom.
|
||||||
|
|
||||||
|
--max-files NUMBER
|
||||||
|
Set the maximum number of files or 0 for no limit.
|
||||||
|
|
||||||
|
Excess files will be discarded.
|
||||||
|
|
||||||
|
--max-file-lag SECONDS
|
||||||
|
Max time files of a commit can take to appear.
|
||||||
|
|
||||||
|
Use -1 for no limit.
|
||||||
|
|
||||||
|
--max-user-speed UNITS
|
||||||
|
Max speed users can travel per second.
|
||||||
|
|
||||||
|
--user-friction SECONDS
|
||||||
|
Time users take to come to a halt.
|
||||||
|
|
||||||
|
--user-scale SCALE
|
||||||
|
Change scale of user avatars.
|
||||||
|
|
||||||
|
--camera-mode MODE
|
||||||
|
Camera mode (overview,track).
|
||||||
|
|
||||||
|
--disable-auto-rotate
|
||||||
|
Disable automatic camera rotation.
|
||||||
|
|
||||||
|
--disable-input
|
||||||
|
Disable keyboard and mouse input.
|
||||||
|
|
||||||
|
--hide DISPLAY_ELEMENT
|
||||||
|
Hide one or more display elements from the list below:
|
||||||
|
|
||||||
|
bloom - bloom effect
|
||||||
|
date - current date
|
||||||
|
dirnames - names of directories
|
||||||
|
files - file icons
|
||||||
|
filenames - names of files
|
||||||
|
mouse - mouse cursor
|
||||||
|
progress - progress bar widget
|
||||||
|
root - root directory of tree
|
||||||
|
tree - animated tree structure
|
||||||
|
users - user avatars
|
||||||
|
usernames - names of users
|
||||||
|
|
||||||
|
Separate multiple elements with commas (eg "mouse,progress")
|
||||||
|
|
||||||
|
--hash-seed SEED
|
||||||
|
Change the seed of hash function.
|
||||||
|
|
||||||
|
--caption-file FILE
|
||||||
|
Caption file (see Caption Log Format).
|
||||||
|
|
||||||
|
--caption-size SIZE
|
||||||
|
Caption size.
|
||||||
|
|
||||||
|
--caption-colour FFFFFF
|
||||||
|
Caption colour in hex.
|
||||||
|
|
||||||
|
--caption-duration SECONDS
|
||||||
|
Caption duration.
|
||||||
|
|
||||||
|
--caption-offset X
|
||||||
|
Caption horizontal offset (0 to centre captions).
|
||||||
|
|
||||||
|
-o, --output-ppm-stream FILE
|
||||||
|
Output a PPM image stream to a file ('-' for STDOUT).
|
||||||
|
|
||||||
|
This will automatically hide the progress bar initially and
|
||||||
|
enable 'stop-at-end' unless other behaviour is specified.
|
||||||
|
|
||||||
|
-r, --output-framerate FPS
|
||||||
|
Framerate of output (25,30,60). Used with --output-ppm-stream.
|
||||||
|
|
||||||
|
--output-custom-log FILE
|
||||||
|
Output a custom format log file ('-' for STDOUT).
|
||||||
|
|
||||||
|
--load-config CONFIG_FILE
|
||||||
|
Load a gource conf file.
|
||||||
|
|
||||||
|
--save-config CONFIG_FILE
|
||||||
|
Save a gource conf file with the current options.
|
||||||
|
|
||||||
|
--path PATH
|
||||||
|
|
||||||
|
path Either a supported version control directory, a pre-generated log
|
||||||
|
file (see log commands or the custom log format), a Gource conf
|
||||||
|
file or '-' to read STDIN.
|
||||||
|
|
||||||
|
If path is omitted, gource will attempt to read a log from the
|
||||||
|
current directory.
|
||||||
|
|
||||||
|
Git, Bazaar, Mercurial and SVN Examples:
|
||||||
|
|
||||||
|
View the log of the repository in the current path:
|
||||||
|
|
||||||
|
gource
|
||||||
|
|
||||||
|
View the log of a project in the specified directory:
|
||||||
|
|
||||||
|
gource my-project-dir
|
||||||
|
|
||||||
|
For large projects, generating a log of the project history may take a long
|
||||||
|
time. For centralized VCS like SVN, generating the log may also put load on
|
||||||
|
the central VCS server.
|
||||||
|
|
||||||
|
In these cases, you may like to save a copy of the log for later use.
|
||||||
|
|
||||||
|
You can generate a log in the VCS specific log format using
|
||||||
|
the --log-command VCS option:
|
||||||
|
|
||||||
|
cd my-svn-project
|
||||||
|
`gource --log-command svn` > my-svn-project.log
|
||||||
|
gource my-svn-project.log
|
||||||
|
|
||||||
|
You can also have Gource write a copy of the log file in its own format:
|
||||||
|
|
||||||
|
gource --output-custom-log my-project-custom.log
|
||||||
|
|
||||||
|
CVS Support:
|
||||||
|
|
||||||
|
Use 'cvs2cl' to generate the log and then pass it to Gource:
|
||||||
|
|
||||||
|
cvs2cl --chrono --stdout --xml -g-q > my-cvs-project.log
|
||||||
|
gource my-cvs-project.log
|
||||||
|
|
||||||
|
Custom Log Format:
|
||||||
|
|
||||||
|
If you want to use Gource with something other than the supported systems,
|
||||||
|
there is a pipe ('|') delimited custom log format:
|
||||||
|
|
||||||
|
timestamp - A unix timestamp of when the update occured.
|
||||||
|
username - The name of the user who made the update.
|
||||||
|
type - initial for the update type - (A)dded, (M)odified or (D)eleted.
|
||||||
|
file - Path of the file updated.
|
||||||
|
colour - A colour for the file in hex (FFFFFF) format. Optional.
|
||||||
|
|
||||||
|
Caption Log Format:
|
||||||
|
|
||||||
|
Gource can display captions along the timeline by specifying a caption file
|
||||||
|
(using --caption-file) in the pipe ('|') delimited format below:
|
||||||
|
|
||||||
|
timestamp - A unix timestamp of when to display the caption.
|
||||||
|
caption - The caption
|
||||||
|
|
||||||
|
Recording Videos:
|
||||||
|
|
||||||
|
See the guide on the homepage for examples of recording videos with Gource:
|
||||||
|
|
||||||
|
https://github.com/acaudwell/Gource/wiki/Videos
|
||||||
|
|
||||||
|
More Information:
|
||||||
|
|
||||||
|
Visit the Gource homepage for guides and examples of using Gource with various
|
||||||
|
version control systems:
|
||||||
|
|
||||||
|
http://gource.io
|
||||||
|
|
||||||
|
Interface:
|
||||||
|
|
||||||
|
The time shown in the top left of the screen is set initially from the first
|
||||||
|
log entry read and is incremented according to the simulation speed
|
||||||
|
(--seconds-per-day).
|
||||||
|
|
||||||
|
Pressing SPACE at any time will pause/resume the simulation. While paused you
|
||||||
|
may use the mouse to inspect the detail of individual files and users.
|
||||||
|
|
||||||
|
TAB cycles through selecting the current visible users.
|
||||||
|
|
||||||
|
The camera mode, either tracking activity or showing the entire code tree, can
|
||||||
|
be toggled using the Middle mouse button.
|
||||||
|
|
||||||
|
You can drag the left mouse button to manually control the camera. The right
|
||||||
|
mouse button rotates the view.
|
||||||
|
|
||||||
|
Interactive keyboard commands:
|
||||||
|
|
||||||
|
(V) Toggle camera mode
|
||||||
|
(C) Displays Gource logo
|
||||||
|
(K) Toggle file extension key
|
||||||
|
(M) Toggle mouse visibility
|
||||||
|
(N) Jump forward in time to next log entry
|
||||||
|
(S) Randomize colours
|
||||||
|
(D) Toggle directory name display mode
|
||||||
|
(F) Toggle file name display mode
|
||||||
|
(U) Toggle user name display mode
|
||||||
|
(G) Toggle display of users
|
||||||
|
(T) Toggle display of directory tree edges
|
||||||
|
(R) Toggle display of root directory edges
|
||||||
|
(+-) Adjust simulation speed
|
||||||
|
(<>) Adjust time scale
|
||||||
|
(TAB) Cycle through visible users
|
||||||
|
(F12) Screenshot
|
||||||
|
(Alt+Enter) Fullscreen toggle
|
||||||
|
(ESC) Quit
|
||||||
|
|
||||||
|
4. Copyright
|
||||||
|
============
|
||||||
|
|
||||||
|
Gource - software version control visualization
|
||||||
|
Copyright (C) 2009 Andrew Caudwell <acaudwell@gmail.com>
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
BIN
gource/SDL2.dll
Normal file
BIN
gource/SDL2.dll
Normal file
Binary file not shown.
BIN
gource/SDL2_image.dll
Normal file
BIN
gource/SDL2_image.dll
Normal file
Binary file not shown.
1
gource/THANKS.txt
Normal file
1
gource/THANKS.txt
Normal file
@@ -0,0 +1 @@
|
|||||||
|
Cheers to everyone at Catalyst IT for their support and encouragement.
|
||||||
3
gource/cmd/gource
Normal file
3
gource/cmd/gource
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
GOURCE_CMD_DIR=`dirname "$0"`
|
||||||
|
"$GOURCE_CMD_DIR/../gource.exe" "$@"
|
||||||
2
gource/cmd/gource.cmd
Normal file
2
gource/cmd/gource.cmd
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
@echo off
|
||||||
|
"%~dp0\..\gource.exe" %*
|
||||||
BIN
gource/data/beam.png
Normal file
BIN
gource/data/beam.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 358 B |
BIN
gource/data/bloom.tga
Normal file
BIN
gource/data/bloom.tga
Normal file
Binary file not shown.
BIN
gource/data/bloom_alpha.tga
Normal file
BIN
gource/data/bloom_alpha.tga
Normal file
Binary file not shown.
BIN
gource/data/file.png
Normal file
BIN
gource/data/file.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 43 KiB |
BIN
gource/data/fonts/FreeSans.ttf
Normal file
BIN
gource/data/fonts/FreeSans.ttf
Normal file
Binary file not shown.
108
gource/data/fonts/README.txt
Normal file
108
gource/data/fonts/README.txt
Normal file
@@ -0,0 +1,108 @@
|
|||||||
|
-*-text-*-
|
||||||
|
GNU FreeFont
|
||||||
|
|
||||||
|
The GNU FreeFont project aims to provide a useful set of free scalable
|
||||||
|
(i.e., OpenType) fonts covering as much as possible of the ISO 10646/Unicode
|
||||||
|
UCS (Universal Character Set).
|
||||||
|
|
||||||
|
Statement of Purpose
|
||||||
|
--------------------
|
||||||
|
|
||||||
|
The practical reason for putting glyphs together in a single font face is
|
||||||
|
to conveniently mix symbols and characters from different writing systems,
|
||||||
|
without having to switch fonts.
|
||||||
|
|
||||||
|
Coverage
|
||||||
|
--------
|
||||||
|
|
||||||
|
FreeFont covers the following character sets
|
||||||
|
|
||||||
|
* ISO 8859 parts 1-15
|
||||||
|
* CEN MES-3 European Unicode Subset
|
||||||
|
http://www.evertype.com/standards/iso10646/pdf/cwa13873.pdf
|
||||||
|
* IBM/Microsoft code pages 437, 850, 852, 1250, 1252 and more
|
||||||
|
* Microsoft/Adobe Windows Glyph List 4 (WGL4)
|
||||||
|
http://www.microsoft.com/typography/otspec/WGL4.htm
|
||||||
|
* KOI8-R and KOI8-RU
|
||||||
|
* DEC VT100 graphics symbols
|
||||||
|
* International Phonetic Alphabet
|
||||||
|
* Arabic, Hebrew, Armenian, Georgian, Ethiopian and Thai alphabets,
|
||||||
|
including Arabic presentation forms A/B
|
||||||
|
* mathematical symbols, including the whole TeX repertoire of symbols
|
||||||
|
* APL symbols
|
||||||
|
etc.
|
||||||
|
|
||||||
|
Editing
|
||||||
|
-------
|
||||||
|
|
||||||
|
The free outline font editor, George Williams's FontForge
|
||||||
|
<http://fontforge.sourceforge.net/> is used for editing the fonts.
|
||||||
|
|
||||||
|
Design Issues
|
||||||
|
-------------
|
||||||
|
|
||||||
|
Which font shapes should be made? Historical style terms like Renaissance
|
||||||
|
or Baroque letterforms cannot be applied beyond Latin/Cyrillic/Greek
|
||||||
|
scripts to any greater extent than Kufi or Nashki can be applied beyond
|
||||||
|
Arabic script; "italic" is really only meaningful for Latin letters.
|
||||||
|
|
||||||
|
However, most modern writing systems have typographic formulations for
|
||||||
|
contrasting uniform and modulated character stroke widths, and have some
|
||||||
|
history with "oblique", faces. Since the advent of the typewriter, most
|
||||||
|
have developed a typographic style with uniform-width characters.
|
||||||
|
|
||||||
|
Accordingly, the FreeFont family has one monospaced - FreeMono - and two
|
||||||
|
proportional faces (one with uniform stroke - FreeSans - and one with
|
||||||
|
modulated stroke - FreeSerif).
|
||||||
|
|
||||||
|
To make text from different writing systems look good side-by-side, each
|
||||||
|
FreeFont face is meant to contain characters of similar style and weight.
|
||||||
|
|
||||||
|
Licensing
|
||||||
|
---------
|
||||||
|
|
||||||
|
Free UCS scalable fonts is free software; you can redistribute it and/or
|
||||||
|
modify it under the terms of the GNU General Public License as published
|
||||||
|
by the Free Software Foundation; either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
The fonts are distributed in the hope that they will be useful, but
|
||||||
|
WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
||||||
|
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||||
|
for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License along
|
||||||
|
with this program; if not, write to the Free Software Foundation, Inc.,
|
||||||
|
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
|
||||||
|
As a special exception, if you create a document which uses this font, and
|
||||||
|
embed this font or unaltered portions of this font into the document, this
|
||||||
|
font does not by itself cause the resulting document to be covered by the
|
||||||
|
GNU General Public License. This exception does not however invalidate any
|
||||||
|
other reasons why the document might be covered by the GNU General Public
|
||||||
|
License. If you modify this font, you may extend this exception to your
|
||||||
|
version of the font, but you are not obligated to do so. If you do not
|
||||||
|
wish to do so, delete this exception statement from your version.
|
||||||
|
|
||||||
|
|
||||||
|
Files and their suffixes
|
||||||
|
------------------------
|
||||||
|
|
||||||
|
The files with .sfd (Spline Font Database) are in FontForge's native format.
|
||||||
|
Please use these if you plan to modify the font files.
|
||||||
|
|
||||||
|
TrueType fonts for immediate consumption are the files with the .ttf
|
||||||
|
(TrueType Font) suffix. These are ready to use in Xwindows based
|
||||||
|
systems using FreeType, on Mac OS, and on older Windows systems.
|
||||||
|
|
||||||
|
OpenType fonts (with suffix .otf) are for use in Windows Vista.
|
||||||
|
Note that although they can be installed on Linux, but many applications
|
||||||
|
in Linux still don't support them.
|
||||||
|
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------
|
||||||
|
Primoz Peterlin, <primoz.peterlin@biofiz.mf.uni-lj.si>
|
||||||
|
Steve White <stevan.white@googlemail.com>
|
||||||
|
|
||||||
|
Free UCS scalable fonts: http://savannah.gnu.org/projects/freefont/
|
||||||
|
$Id: README,v 1.7 2009/01/13 08:43:23 Stevan_White Exp $
|
||||||
5
gource/data/gource.style
Normal file
5
gource/data/gource.style
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
changeset = '{file_adds}{file_copies}{file_mods}{file_dels}'
|
||||||
|
file_mod = "{date|hgdate}|{author|person}|M|{file_mod}\n"
|
||||||
|
file_add = "{date|hgdate}|{author|person}|A|{file_add}\n"
|
||||||
|
file_del = "{date|hgdate}|{author|person}|D|{file_del}\n"
|
||||||
|
file_copy = "{date|hgdate}|{author|person}|A|{name}\n"
|
||||||
16
gource/data/shaders/bloom.frag
Normal file
16
gource/data/shaders/bloom.frag
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
|
||||||
|
varying vec3 pos;
|
||||||
|
|
||||||
|
void main()
|
||||||
|
{
|
||||||
|
float r = fract(sin(dot(pos.xy ,vec2(11.3713,67.3219))) * 2351.3718);
|
||||||
|
|
||||||
|
float offset = (0.5 - r) * gl_TexCoord[0].x * 0.045;
|
||||||
|
|
||||||
|
float intensity = min(1.0, cos((length(pos*2.0)+offset)/gl_TexCoord[0].x));
|
||||||
|
float gradient = intensity * smoothstep(0.0, 2.0, intensity);
|
||||||
|
|
||||||
|
gradient *= smoothstep(1.0,0.67+r*0.33, 1.0-intensity);
|
||||||
|
|
||||||
|
gl_FragColor = gl_Color * gradient;
|
||||||
|
}
|
||||||
10
gource/data/shaders/bloom.vert
Normal file
10
gource/data/shaders/bloom.vert
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
|
||||||
|
varying vec3 pos;
|
||||||
|
|
||||||
|
void main()
|
||||||
|
{
|
||||||
|
pos = gl_Vertex.xyz - gl_MultiTexCoord0.yzw;
|
||||||
|
gl_TexCoord[0] = gl_MultiTexCoord0;
|
||||||
|
gl_FrontColor = gl_Color;
|
||||||
|
gl_Position = ftransform();
|
||||||
|
}
|
||||||
9
gource/data/shaders/shadow.frag
Normal file
9
gource/data/shaders/shadow.frag
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
uniform sampler2D tex;
|
||||||
|
uniform float shadow_strength;
|
||||||
|
|
||||||
|
void main(void)
|
||||||
|
{
|
||||||
|
vec4 colour = texture2D(tex,gl_TexCoord[0].st);
|
||||||
|
|
||||||
|
gl_FragColor = vec4(0.0, 0.0, 0.0, gl_Color.w * colour.w * shadow_strength);
|
||||||
|
}
|
||||||
6
gource/data/shaders/shadow.vert
Normal file
6
gource/data/shaders/shadow.vert
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
void main(void)
|
||||||
|
{
|
||||||
|
gl_TexCoord[0] = gl_MultiTexCoord0;
|
||||||
|
gl_FrontColor = gl_Color;
|
||||||
|
gl_Position = ftransform();
|
||||||
|
}
|
||||||
15
gource/data/shaders/text.frag
Normal file
15
gource/data/shaders/text.frag
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
uniform sampler2D tex;
|
||||||
|
uniform float shadow_strength;
|
||||||
|
uniform float texel_size;
|
||||||
|
|
||||||
|
void main(void)
|
||||||
|
{
|
||||||
|
float colour_alpha = texture2D(tex,gl_TexCoord[0].xy).w;
|
||||||
|
float shadow_alpha = texture2D(tex,gl_TexCoord[0].xy - vec2(texel_size)).w * shadow_strength;
|
||||||
|
|
||||||
|
float combined_alpha = 1.0 - (1.0-shadow_alpha)*(1.0-colour_alpha);
|
||||||
|
|
||||||
|
if(combined_alpha > 0.0) colour_alpha /= combined_alpha;
|
||||||
|
|
||||||
|
gl_FragColor = gl_Color * vec4(vec3(colour_alpha), combined_alpha);
|
||||||
|
}
|
||||||
6
gource/data/shaders/text.vert
Normal file
6
gource/data/shaders/text.vert
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
void main(void)
|
||||||
|
{
|
||||||
|
gl_TexCoord[0] = gl_MultiTexCoord0;
|
||||||
|
gl_FrontColor = gl_Color;
|
||||||
|
gl_Position = ftransform();
|
||||||
|
}
|
||||||
BIN
gource/data/user.png
Normal file
BIN
gource/data/user.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 61 KiB |
BIN
gource/glew32.dll
Normal file
BIN
gource/glew32.dll
Normal file
Binary file not shown.
BIN
gource/gource.exe
Normal file
BIN
gource/gource.exe
Normal file
Binary file not shown.
BIN
gource/libboost_filesystem-mt.dll
Normal file
BIN
gource/libboost_filesystem-mt.dll
Normal file
Binary file not shown.
BIN
gource/libbz2-1.dll
Normal file
BIN
gource/libbz2-1.dll
Normal file
Binary file not shown.
BIN
gource/libfreetype-6.dll
Normal file
BIN
gource/libfreetype-6.dll
Normal file
Binary file not shown.
BIN
gource/libgcc_s_seh-1.dll
Normal file
BIN
gource/libgcc_s_seh-1.dll
Normal file
Binary file not shown.
BIN
gource/libglib-2.0-0.dll
Normal file
BIN
gource/libglib-2.0-0.dll
Normal file
Binary file not shown.
BIN
gource/libgraphite2.dll
Normal file
BIN
gource/libgraphite2.dll
Normal file
Binary file not shown.
BIN
gource/libharfbuzz-0.dll
Normal file
BIN
gource/libharfbuzz-0.dll
Normal file
Binary file not shown.
BIN
gource/libiconv-2.dll
Normal file
BIN
gource/libiconv-2.dll
Normal file
Binary file not shown.
BIN
gource/libintl-8.dll
Normal file
BIN
gource/libintl-8.dll
Normal file
Binary file not shown.
BIN
gource/libjpeg-8.dll
Normal file
BIN
gource/libjpeg-8.dll
Normal file
Binary file not shown.
BIN
gource/liblzma-5.dll
Normal file
BIN
gource/liblzma-5.dll
Normal file
Binary file not shown.
BIN
gource/libpcre-1.dll
Normal file
BIN
gource/libpcre-1.dll
Normal file
Binary file not shown.
BIN
gource/libpng16-16.dll
Normal file
BIN
gource/libpng16-16.dll
Normal file
Binary file not shown.
BIN
gource/libstdc++-6.dll
Normal file
BIN
gource/libstdc++-6.dll
Normal file
Binary file not shown.
BIN
gource/libtiff-5.dll
Normal file
BIN
gource/libtiff-5.dll
Normal file
Binary file not shown.
BIN
gource/libwebp-7.dll
Normal file
BIN
gource/libwebp-7.dll
Normal file
Binary file not shown.
BIN
gource/libwinpthread-1.dll
Normal file
BIN
gource/libwinpthread-1.dll
Normal file
Binary file not shown.
BIN
gource/libzstd.dll
Normal file
BIN
gource/libzstd.dll
Normal file
Binary file not shown.
BIN
gource/zlib1.dll
Normal file
BIN
gource/zlib1.dll
Normal file
Binary file not shown.
@@ -20,7 +20,6 @@ pluginManagement {
|
|||||||
mavenLocal()
|
mavenLocal()
|
||||||
mavenCentral()
|
mavenCentral()
|
||||||
gradlePluginPortal()
|
gradlePluginPortal()
|
||||||
maven { url "https://dl.cloudsmith.io/public/arcane/archive/maven/" }
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
rootProject.name = 'Iris'
|
rootProject.name = 'Iris'
|
||||||
@@ -23,9 +23,13 @@ import com.google.gson.JsonParseException;
|
|||||||
import com.google.gson.JsonParser;
|
import com.google.gson.JsonParser;
|
||||||
import com.volmit.iris.core.IrisSettings;
|
import com.volmit.iris.core.IrisSettings;
|
||||||
import com.volmit.iris.core.ServerConfigurator;
|
import com.volmit.iris.core.ServerConfigurator;
|
||||||
import com.volmit.iris.core.link.*;
|
import com.volmit.iris.core.link.IrisPapiExpansion;
|
||||||
|
import com.volmit.iris.core.link.MultiverseCoreLink;
|
||||||
|
import com.volmit.iris.core.link.MythicMobsLink;
|
||||||
import com.volmit.iris.core.loader.IrisData;
|
import com.volmit.iris.core.loader.IrisData;
|
||||||
import com.volmit.iris.core.nms.INMS;
|
import com.volmit.iris.core.nms.INMS;
|
||||||
|
import com.volmit.iris.core.nms.v20.NMSBinding1_20_1;
|
||||||
|
import com.volmit.iris.core.pregenerator.LazyPregenerator;
|
||||||
import com.volmit.iris.core.service.StudioSVC;
|
import com.volmit.iris.core.service.StudioSVC;
|
||||||
import com.volmit.iris.core.tools.IrisToolbelt;
|
import com.volmit.iris.core.tools.IrisToolbelt;
|
||||||
import com.volmit.iris.engine.EnginePanic;
|
import com.volmit.iris.engine.EnginePanic;
|
||||||
@@ -40,7 +44,10 @@ import com.volmit.iris.util.exceptions.IrisException;
|
|||||||
import com.volmit.iris.util.format.C;
|
import com.volmit.iris.util.format.C;
|
||||||
import com.volmit.iris.util.format.Form;
|
import com.volmit.iris.util.format.Form;
|
||||||
import com.volmit.iris.util.function.NastyRunnable;
|
import com.volmit.iris.util.function.NastyRunnable;
|
||||||
import com.volmit.iris.util.io.*;
|
import com.volmit.iris.util.io.FileWatcher;
|
||||||
|
import com.volmit.iris.util.io.IO;
|
||||||
|
import com.volmit.iris.util.io.InstanceState;
|
||||||
|
import com.volmit.iris.util.io.JarScanner;
|
||||||
import com.volmit.iris.util.math.M;
|
import com.volmit.iris.util.math.M;
|
||||||
import com.volmit.iris.util.math.RNG;
|
import com.volmit.iris.util.math.RNG;
|
||||||
import com.volmit.iris.util.parallel.MultiBurst;
|
import com.volmit.iris.util.parallel.MultiBurst;
|
||||||
@@ -58,11 +65,11 @@ import net.kyori.adventure.text.serializer.ComponentSerializer;
|
|||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
import org.bukkit.GameMode;
|
import org.bukkit.GameMode;
|
||||||
import org.bukkit.Location;
|
import org.bukkit.Location;
|
||||||
import org.bukkit.World;
|
|
||||||
import org.bukkit.WorldCreator;
|
import org.bukkit.WorldCreator;
|
||||||
import org.bukkit.block.data.BlockData;
|
import org.bukkit.block.data.BlockData;
|
||||||
import org.bukkit.command.Command;
|
import org.bukkit.command.Command;
|
||||||
import org.bukkit.command.CommandSender;
|
import org.bukkit.command.CommandSender;
|
||||||
|
import org.bukkit.configuration.ConfigurationSection;
|
||||||
import org.bukkit.configuration.file.FileConfiguration;
|
import org.bukkit.configuration.file.FileConfiguration;
|
||||||
import org.bukkit.configuration.file.YamlConfiguration;
|
import org.bukkit.configuration.file.YamlConfiguration;
|
||||||
import org.bukkit.entity.Player;
|
import org.bukkit.entity.Player;
|
||||||
@@ -81,11 +88,13 @@ import java.lang.annotation.Annotation;
|
|||||||
import java.net.URL;
|
import java.net.URL;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Objects;
|
|
||||||
|
|
||||||
@SuppressWarnings("CanBeFinal")
|
@SuppressWarnings("CanBeFinal")
|
||||||
public class Iris extends VolmitPlugin implements Listener {
|
public class Iris extends VolmitPlugin implements Listener {
|
||||||
|
public static final String OVERWORLD_TAG = "3620";
|
||||||
|
|
||||||
private static final Queue<Runnable> syncJobs = new ShurikenQueue<>();
|
private static final Queue<Runnable> syncJobs = new ShurikenQueue<>();
|
||||||
|
|
||||||
public static Iris instance;
|
public static Iris instance;
|
||||||
public static BukkitAudiences audiences;
|
public static BukkitAudiences audiences;
|
||||||
public static MultiverseCoreLink linkMultiverseCore;
|
public static MultiverseCoreLink linkMultiverseCore;
|
||||||
@@ -98,7 +107,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
try {
|
try {
|
||||||
fixShading();
|
fixShading();
|
||||||
InstanceState.updateInstanceId();
|
InstanceState.updateInstanceId();
|
||||||
} catch(Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -116,7 +125,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void callEvent(Event e) {
|
public static void callEvent(Event e) {
|
||||||
if(!e.isAsynchronous()) {
|
if (!e.isAsynchronous()) {
|
||||||
J.s(() -> Bukkit.getPluginManager().callEvent(e));
|
J.s(() -> Bukkit.getPluginManager().callEvent(e));
|
||||||
} else {
|
} else {
|
||||||
Bukkit.getPluginManager().callEvent(e);
|
Bukkit.getPluginManager().callEvent(e);
|
||||||
@@ -127,11 +136,11 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
JarScanner js = new JarScanner(instance.getJarFile(), s);
|
JarScanner js = new JarScanner(instance.getJarFile(), s);
|
||||||
KList<Object> v = new KList<>();
|
KList<Object> v = new KList<>();
|
||||||
J.attempt(js::scan);
|
J.attempt(js::scan);
|
||||||
for(Class<?> i : js.getClasses()) {
|
for (Class<?> i : js.getClasses()) {
|
||||||
if(slicedClass == null || i.isAnnotationPresent(slicedClass)) {
|
if (slicedClass == null || i.isAnnotationPresent(slicedClass)) {
|
||||||
try {
|
try {
|
||||||
v.add(i.getDeclaredConstructor().newInstance());
|
v.add(i.getDeclaredConstructor().newInstance());
|
||||||
} catch(Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -144,11 +153,11 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
JarScanner js = new JarScanner(instance.getJarFile(), s);
|
JarScanner js = new JarScanner(instance.getJarFile(), s);
|
||||||
KList<Class<?>> v = new KList<>();
|
KList<Class<?>> v = new KList<>();
|
||||||
J.attempt(js::scan);
|
J.attempt(js::scan);
|
||||||
for(Class<?> i : js.getClasses()) {
|
for (Class<?> i : js.getClasses()) {
|
||||||
if(slicedClass == null || i.isAnnotationPresent(slicedClass)) {
|
if (slicedClass == null || i.isAnnotationPresent(slicedClass)) {
|
||||||
try {
|
try {
|
||||||
v.add(i);
|
v.add(i);
|
||||||
} catch(Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -162,7 +171,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void sq(Runnable r) {
|
public static void sq(Runnable r) {
|
||||||
synchronized(syncJobs) {
|
synchronized (syncJobs) {
|
||||||
syncJobs.queue(r);
|
syncJobs.queue(r);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -174,27 +183,28 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
public static void msg(String string) {
|
public static void msg(String string) {
|
||||||
try {
|
try {
|
||||||
sender.sendMessage(string);
|
sender.sendMessage(string);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
try {
|
try {
|
||||||
System.out.println(instance.getTag() + string.replaceAll("(<([^>]+)>)", ""));
|
System.out.println(instance.getTag() + string.replaceAll("(<([^>]+)>)", ""));
|
||||||
} catch(Throwable ignored1) {
|
} catch (Throwable ignored1) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static File getCached(String name, String url) {
|
public static File getCached(String name, String url) {
|
||||||
String h = IO.hash(name + "@" + url);
|
String h = IO.hash(name + "@" + url);
|
||||||
File f = Iris.instance.getDataFile("cache", h.substring(0, 2), h.substring(3, 5), h);
|
File f = Iris.instance.getDataFile("cache", h.substring(0, 2), h.substring(3, 5), h);
|
||||||
|
|
||||||
if(!f.exists()) {
|
if (!f.exists()) {
|
||||||
try(BufferedInputStream in = new BufferedInputStream(new URL(url).openStream()); FileOutputStream fileOutputStream = new FileOutputStream(f)) {
|
try (BufferedInputStream in = new BufferedInputStream(new URL(url).openStream()); FileOutputStream fileOutputStream = new FileOutputStream(f)) {
|
||||||
byte[] dataBuffer = new byte[1024];
|
byte[] dataBuffer = new byte[1024];
|
||||||
int bytesRead;
|
int bytesRead;
|
||||||
while((bytesRead = in.read(dataBuffer, 0, 1024)) != -1) {
|
while ((bytesRead = in.read(dataBuffer, 0, 1024)) != -1) {
|
||||||
fileOutputStream.write(dataBuffer, 0, bytesRead);
|
fileOutputStream.write(dataBuffer, 0, bytesRead);
|
||||||
Iris.verbose("Aquiring " + name);
|
Iris.verbose("Aquiring " + name);
|
||||||
}
|
}
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -206,19 +216,19 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
String h = IO.hash(name + "*" + url);
|
String h = IO.hash(name + "*" + url);
|
||||||
File f = Iris.instance.getDataFile("cache", h.substring(0, 2), h.substring(3, 5), h);
|
File f = Iris.instance.getDataFile("cache", h.substring(0, 2), h.substring(3, 5), h);
|
||||||
|
|
||||||
try(BufferedInputStream in = new BufferedInputStream(new URL(url).openStream()); FileOutputStream fileOutputStream = new FileOutputStream(f)) {
|
try (BufferedInputStream in = new BufferedInputStream(new URL(url).openStream()); FileOutputStream fileOutputStream = new FileOutputStream(f)) {
|
||||||
byte[] dataBuffer = new byte[1024];
|
byte[] dataBuffer = new byte[1024];
|
||||||
int bytesRead;
|
int bytesRead;
|
||||||
while((bytesRead = in.read(dataBuffer, 0, 1024)) != -1) {
|
while ((bytesRead = in.read(dataBuffer, 0, 1024)) != -1) {
|
||||||
fileOutputStream.write(dataBuffer, 0, bytesRead);
|
fileOutputStream.write(dataBuffer, 0, bytesRead);
|
||||||
}
|
}
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
return IO.readAll(f);
|
return IO.readAll(f);
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -229,15 +239,15 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
String h = IO.hash(name + "*" + url);
|
String h = IO.hash(name + "*" + url);
|
||||||
File f = Iris.instance.getDataFile("cache", h.substring(0, 2), h.substring(3, 5), h);
|
File f = Iris.instance.getDataFile("cache", h.substring(0, 2), h.substring(3, 5), h);
|
||||||
Iris.verbose("Download " + name + " -> " + url);
|
Iris.verbose("Download " + name + " -> " + url);
|
||||||
try(BufferedInputStream in = new BufferedInputStream(new URL(url).openStream()); FileOutputStream fileOutputStream = new FileOutputStream(f)) {
|
try (BufferedInputStream in = new BufferedInputStream(new URL(url).openStream()); FileOutputStream fileOutputStream = new FileOutputStream(f)) {
|
||||||
byte[] dataBuffer = new byte[1024];
|
byte[] dataBuffer = new byte[1024];
|
||||||
int bytesRead;
|
int bytesRead;
|
||||||
while((bytesRead = in.read(dataBuffer, 0, 1024)) != -1) {
|
while ((bytesRead = in.read(dataBuffer, 0, 1024)) != -1) {
|
||||||
fileOutputStream.write(dataBuffer, 0, bytesRead);
|
fileOutputStream.write(dataBuffer, 0, bytesRead);
|
||||||
}
|
}
|
||||||
|
|
||||||
fileOutputStream.flush();
|
fileOutputStream.flush();
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
@@ -254,32 +264,32 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void debug(String string) {
|
public static void debug(String string) {
|
||||||
if(!IrisSettings.get().getGeneral().isDebug()) {
|
if (!IrisSettings.get().getGeneral().isDebug()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
throw new RuntimeException();
|
throw new RuntimeException();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
try {
|
try {
|
||||||
String[] cc = e.getStackTrace()[1].getClassName().split("\\Q.\\E");
|
String[] cc = e.getStackTrace()[1].getClassName().split("\\Q.\\E");
|
||||||
|
|
||||||
if(cc.length > 5) {
|
if (cc.length > 5) {
|
||||||
debug(cc[3] + "/" + cc[4] + "/" + cc[cc.length - 1], e.getStackTrace()[1].getLineNumber(), string);
|
debug(cc[3] + "/" + cc[4] + "/" + cc[cc.length - 1], e.getStackTrace()[1].getLineNumber(), string);
|
||||||
} else {
|
} else {
|
||||||
debug(cc[3] + "/" + cc[4], e.getStackTrace()[1].getLineNumber(), string);
|
debug(cc[3] + "/" + cc[4], e.getStackTrace()[1].getLineNumber(), string);
|
||||||
}
|
}
|
||||||
} catch(Throwable ex) {
|
} catch (Throwable ex) {
|
||||||
debug("Origin", -1, string);
|
debug("Origin", -1, string);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void debug(String category, int line, String string) {
|
public static void debug(String category, int line, String string) {
|
||||||
if(!IrisSettings.get().getGeneral().isDebug()) {
|
if (!IrisSettings.get().getGeneral().isDebug()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(IrisSettings.get().getGeneral().isUseConsoleCustomColors()) {
|
if (IrisSettings.get().getGeneral().isUseConsoleCustomColors()) {
|
||||||
msg("<gradient:#095fe0:#a848db>" + category + " <#bf3b76>" + line + "<reset> " + C.LIGHT_PURPLE + string.replaceAll("\\Q<\\E", "[").replaceAll("\\Q>\\E", "]"));
|
msg("<gradient:#095fe0:#a848db>" + category + " <#bf3b76>" + line + "<reset> " + C.LIGHT_PURPLE + string.replaceAll("\\Q<\\E", "[").replaceAll("\\Q>\\E", "]"));
|
||||||
} else {
|
} else {
|
||||||
msg(C.BLUE + category + ":" + C.AQUA + line + C.RESET + C.LIGHT_PURPLE + " " + string.replaceAll("\\Q<\\E", "[").replaceAll("\\Q>\\E", "]"));
|
msg(C.BLUE + category + ":" + C.AQUA + line + C.RESET + C.LIGHT_PURPLE + " " + string.replaceAll("\\Q<\\E", "[").replaceAll("\\Q>\\E", "]"));
|
||||||
@@ -295,8 +305,8 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
msg(C.IRIS + string);
|
msg(C.IRIS + string);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void info(String string) {
|
public static void info(String format, Object... args) {
|
||||||
msg(C.WHITE + string);
|
msg(C.WHITE + String.format(format, args));
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings("deprecation")
|
@SuppressWarnings("deprecation")
|
||||||
@@ -306,12 +316,12 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
object.run();
|
object.run();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
}, RNG.r.i(100, 1200));
|
}, RNG.r.i(100, 1200));
|
||||||
} catch(IllegalPluginAccessException ignored) {
|
} catch (IllegalPluginAccessException ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -321,18 +331,18 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void clearQueues() {
|
public static void clearQueues() {
|
||||||
synchronized(syncJobs) {
|
synchronized (syncJobs) {
|
||||||
syncJobs.clear();
|
syncJobs.clear();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static int getJavaVersion() {
|
private static int getJavaVersion() {
|
||||||
String version = System.getProperty("java.version");
|
String version = System.getProperty("java.version");
|
||||||
if(version.startsWith("1.")) {
|
if (version.startsWith("1.")) {
|
||||||
version = version.substring(2, 3);
|
version = version.substring(2, 3);
|
||||||
} else {
|
} else {
|
||||||
int dot = version.indexOf(".");
|
int dot = version.indexOf(".");
|
||||||
if(dot != -1) {
|
if (dot != -1) {
|
||||||
version = version.substring(0, dot);
|
version = version.substring(0, dot);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -340,10 +350,10 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void reportErrorChunk(int x, int z, Throwable e, String extra) {
|
public static void reportErrorChunk(int x, int z, Throwable e, String extra) {
|
||||||
if(IrisSettings.get().getGeneral().isDebug()) {
|
if (IrisSettings.get().getGeneral().isDebug()) {
|
||||||
File f = instance.getDataFile("debug", "chunk-errors", "chunk." + x + "." + z + ".txt");
|
File f = instance.getDataFile("debug", "chunk-errors", "chunk." + x + "." + z + ".txt");
|
||||||
|
|
||||||
if(!f.exists()) {
|
if (!f.exists()) {
|
||||||
J.attempt(() -> {
|
J.attempt(() -> {
|
||||||
PrintWriter pw = new PrintWriter(f);
|
PrintWriter pw = new PrintWriter(f);
|
||||||
pw.println("Thread: " + Thread.currentThread().getName());
|
pw.println("Thread: " + Thread.currentThread().getName());
|
||||||
@@ -358,16 +368,16 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void reportError(Throwable e) {
|
public static void reportError(Throwable e) {
|
||||||
if(IrisSettings.get().getGeneral().isDebug()) {
|
if (IrisSettings.get().getGeneral().isDebug()) {
|
||||||
String n = e.getClass().getCanonicalName() + "-" + e.getStackTrace()[0].getClassName() + "-" + e.getStackTrace()[0].getLineNumber();
|
String n = e.getClass().getCanonicalName() + "-" + e.getStackTrace()[0].getClassName() + "-" + e.getStackTrace()[0].getLineNumber();
|
||||||
|
|
||||||
if(e.getCause() != null) {
|
if (e.getCause() != null) {
|
||||||
n += "-" + e.getCause().getStackTrace()[0].getClassName() + "-" + e.getCause().getStackTrace()[0].getLineNumber();
|
n += "-" + e.getCause().getStackTrace()[0].getClassName() + "-" + e.getCause().getStackTrace()[0].getLineNumber();
|
||||||
}
|
}
|
||||||
|
|
||||||
File f = instance.getDataFile("debug", "caught-exceptions", n + ".txt");
|
File f = instance.getDataFile("debug", "caught-exceptions", n + ".txt");
|
||||||
|
|
||||||
if(!f.exists()) {
|
if (!f.exists()) {
|
||||||
J.attempt(() -> {
|
J.attempt(() -> {
|
||||||
PrintWriter pw = new PrintWriter(f);
|
PrintWriter pw = new PrintWriter(f);
|
||||||
pw.println("Thread: " + Thread.currentThread().getName());
|
pw.println("Thread: " + Thread.currentThread().getName());
|
||||||
@@ -381,6 +391,44 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static void dump() {
|
||||||
|
try {
|
||||||
|
File fi = Iris.instance.getDataFile("dump", "td-" + new java.sql.Date(M.ms()) + ".txt");
|
||||||
|
FileOutputStream fos = new FileOutputStream(fi);
|
||||||
|
Map<Thread, StackTraceElement[]> f = Thread.getAllStackTraces();
|
||||||
|
PrintWriter pw = new PrintWriter(fos);
|
||||||
|
for (Thread i : f.keySet()) {
|
||||||
|
pw.println("========================================");
|
||||||
|
pw.println("Thread: '" + i.getName() + "' ID: " + i.getId() + " STATUS: " + i.getState().name());
|
||||||
|
|
||||||
|
for (StackTraceElement j : f.get(i)) {
|
||||||
|
pw.println(" @ " + j.toString());
|
||||||
|
}
|
||||||
|
|
||||||
|
pw.println("========================================");
|
||||||
|
pw.println();
|
||||||
|
pw.println();
|
||||||
|
}
|
||||||
|
|
||||||
|
pw.close();
|
||||||
|
System.out.println("DUMPED! See " + fi.getAbsolutePath());
|
||||||
|
} catch (Throwable e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void panic() {
|
||||||
|
EnginePanic.panic();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void addPanic(String s, String v) {
|
||||||
|
EnginePanic.add(s, v);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void fixShading() {
|
||||||
|
ShadeFix.fix(ComponentSerializer.class);
|
||||||
|
}
|
||||||
|
|
||||||
private void enable() {
|
private void enable() {
|
||||||
instance = this;
|
instance = this;
|
||||||
services = new KMap<>();
|
services = new KMap<>();
|
||||||
@@ -400,6 +448,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
J.s(() -> {
|
J.s(() -> {
|
||||||
J.a(() -> PaperLib.suggestPaper(this));
|
J.a(() -> PaperLib.suggestPaper(this));
|
||||||
J.a(() -> IO.delete(getTemp()));
|
J.a(() -> IO.delete(getTemp()));
|
||||||
|
J.a(LazyPregenerator::loadLazyGenerators, 100);
|
||||||
J.a(this::bstats);
|
J.a(this::bstats);
|
||||||
J.ar(this::checkConfigHotload, 60);
|
J.ar(this::checkConfigHotload, 60);
|
||||||
J.sr(this::tickQueue, 0);
|
J.sr(this::tickQueue, 0);
|
||||||
@@ -417,55 +466,58 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
FileConfiguration fc = new YamlConfiguration();
|
FileConfiguration fc = new YamlConfiguration();
|
||||||
try {
|
try {
|
||||||
fc.load(new File("bukkit.yml"));
|
fc.load(new File("bukkit.yml"));
|
||||||
searching: for(String i : fc.getKeys(true))
|
ConfigurationSection section = fc.getConfigurationSection("worlds");
|
||||||
{
|
if (section == null) {
|
||||||
if(i.startsWith("worlds.") && i.endsWith(".generator")) {
|
return;
|
||||||
String worldName = i.split("\\Q.\\E")[1];
|
}
|
||||||
String generator = IrisSettings.get().getGenerator().getDefaultWorldType();
|
|
||||||
if(fc.getString(i).startsWith("Iris:")) {
|
|
||||||
generator = fc.getString(i).split("\\Q:\\E")[1];
|
|
||||||
} else if(fc.getString(i).equals("Iris")) {
|
|
||||||
generator = IrisSettings.get().getGenerator().getDefaultWorldType();
|
|
||||||
} else {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(World j : Bukkit.getWorlds())
|
for (String s : section.getKeys(false)) {
|
||||||
{
|
ConfigurationSection entry = section.getConfigurationSection(s);
|
||||||
if(j.getName().equals(worldName))
|
if (!entry.contains("generator", true)) {
|
||||||
{
|
continue;
|
||||||
continue searching;
|
}
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Iris.warn("Detected an Iris World in the bukkit yml '" + worldName + "' using Iris that was not loaded by bukkit. Good Guy Iris will load it up for you!");
|
String generator = entry.getString("generator");
|
||||||
Iris.info(C.LIGHT_PURPLE + "Preparing Spawn for " + worldName + "' using Iris:" + generator);
|
if (generator.startsWith("Iris:")) {
|
||||||
World world = new WorldCreator(worldName)
|
generator = generator.split("\\Q:\\E")[1];
|
||||||
.generator(getDefaultWorldGenerator(worldName, generator))
|
} else if (generator.equalsIgnoreCase("Iris")) {
|
||||||
|
generator = IrisSettings.get().getGenerator().getDefaultWorldType();
|
||||||
|
} else {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
Iris.info("2 World: %s | Generator: %s", s, generator);
|
||||||
|
|
||||||
|
if (Bukkit.getWorlds().stream().anyMatch(w -> w.getName().equals(s))) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
Iris.info(C.LIGHT_PURPLE + "Preparing Spawn for " + s + "' using Iris:" + generator + "...");
|
||||||
|
new WorldCreator(s)
|
||||||
|
.generator(getDefaultWorldGenerator(s, generator))
|
||||||
.environment(IrisData.loadAnyDimension(generator).getEnvironment())
|
.environment(IrisData.loadAnyDimension(generator).getEnvironment())
|
||||||
.createWorld();
|
.createWorld();
|
||||||
Iris.info(C.LIGHT_PURPLE + "Loaded " + worldName + "!");
|
Iris.info(C.LIGHT_PURPLE + "Loaded " + s + "!");
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void autoStartStudio() {
|
private void autoStartStudio() {
|
||||||
if(IrisSettings.get().getStudio().isAutoStartDefaultStudio()) {
|
if (IrisSettings.get().getStudio().isAutoStartDefaultStudio()) {
|
||||||
Iris.info("Starting up auto Studio!");
|
Iris.info("Starting up auto Studio!");
|
||||||
try {
|
try {
|
||||||
Player r = new KList<>(getServer().getOnlinePlayers()).getRandom();
|
Player r = new KList<>(getServer().getOnlinePlayers()).getRandom();
|
||||||
Iris.service(StudioSVC.class).open(r != null ? new VolmitSender(r) : sender, 1337, IrisSettings.get().getGenerator().getDefaultWorldType(), (w) -> {
|
Iris.service(StudioSVC.class).open(r != null ? new VolmitSender(r) : sender, 1337, IrisSettings.get().getGenerator().getDefaultWorldType(), (w) -> {
|
||||||
J.s(() -> {
|
J.s(() -> {
|
||||||
for(Player i : getServer().getOnlinePlayers()) {
|
for (Player i : getServer().getOnlinePlayers()) {
|
||||||
i.setGameMode(GameMode.SPECTATOR);
|
i.setGameMode(GameMode.SPECTATOR);
|
||||||
i.teleport(new Location(w, 0, 200, 0));
|
i.teleport(new Location(w, 0, 200, 0));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
} catch(IrisException e) {
|
} catch (IrisException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -474,7 +526,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
private void setupAudience() {
|
private void setupAudience() {
|
||||||
try {
|
try {
|
||||||
audiences = BukkitAudiences.create(this);
|
audiences = BukkitAudiences.create(this);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
IrisSettings.get().getGeneral().setUseConsoleCustomColors(false);
|
IrisSettings.get().getGeneral().setUseConsoleCustomColors(false);
|
||||||
IrisSettings.get().getGeneral().setUseCustomColorsIngame(false);
|
IrisSettings.get().getGeneral().setUseCustomColorsIngame(false);
|
||||||
@@ -482,48 +534,15 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void dump() {
|
|
||||||
try {
|
|
||||||
File fi = Iris.instance.getDataFile("dump", "td-" + new java.sql.Date(M.ms()) + ".txt");
|
|
||||||
FileOutputStream fos = new FileOutputStream(fi);
|
|
||||||
Map<Thread, StackTraceElement[]> f = Thread.getAllStackTraces();
|
|
||||||
PrintWriter pw = new PrintWriter(fos);
|
|
||||||
for(Thread i : f.keySet()) {
|
|
||||||
pw.println("========================================");
|
|
||||||
pw.println("Thread: '" + i.getName() + "' ID: " + i.getId() + " STATUS: " + i.getState().name());
|
|
||||||
|
|
||||||
for(StackTraceElement j : f.get(i)) {
|
|
||||||
pw.println(" @ " + j.toString());
|
|
||||||
}
|
|
||||||
|
|
||||||
pw.println("========================================");
|
|
||||||
pw.println();
|
|
||||||
pw.println();
|
|
||||||
}
|
|
||||||
|
|
||||||
pw.close();
|
|
||||||
System.out.println("DUMPED! See " + fi.getAbsolutePath());
|
|
||||||
} catch(Throwable e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void postShutdown(Runnable r) {
|
public void postShutdown(Runnable r) {
|
||||||
postShutdown.add(r);
|
postShutdown.add(r);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void panic() {
|
|
||||||
EnginePanic.panic();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void addPanic(String s, String v) {
|
|
||||||
EnginePanic.add(s, v);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void onEnable() {
|
public void onEnable() {
|
||||||
enable();
|
enable();
|
||||||
super.onEnable();
|
super.onEnable();
|
||||||
Bukkit.getPluginManager().registerEvents(this, this);
|
Bukkit.getPluginManager().registerEvents(this, this);
|
||||||
|
setupChecks();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void onDisable() {
|
public void onDisable() {
|
||||||
@@ -536,12 +555,8 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
super.onDisable();
|
super.onDisable();
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void fixShading() {
|
|
||||||
ShadeFix.fix(ComponentSerializer.class);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void setupPapi() {
|
private void setupPapi() {
|
||||||
if(Bukkit.getPluginManager().getPlugin("PlaceholderAPI") != null) {
|
if (Bukkit.getPluginManager().getPlugin("PlaceholderAPI") != null) {
|
||||||
new IrisPapiExpansion().register();
|
new IrisPapiExpansion().register();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -561,8 +576,33 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
return C.BOLD + "" + C.DARK_GRAY + "[" + C.BOLD + "" + C.IRIS + "Iris" + C.BOLD + C.DARK_GRAY + "]" + C.RESET + "" + C.GRAY + ": ";
|
return C.BOLD + "" + C.DARK_GRAY + "[" + C.BOLD + "" + C.IRIS + "Iris" + C.BOLD + C.DARK_GRAY + "]" + C.RESET + "" + C.GRAY + ": ";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean setupChecks() {
|
||||||
|
boolean passed = true;
|
||||||
|
Iris.info("Version Information: " + instance.getServer().getVersion() + " | " + instance.getServer().getBukkitVersion());
|
||||||
|
if (!instance.getServer().getBukkitVersion().contains(NMSBinding1_20_1.NMS_VERSION)) {
|
||||||
|
passed = false;
|
||||||
|
Iris.warn("============================================");
|
||||||
|
Iris.warn("=");
|
||||||
|
Iris.warn("=");
|
||||||
|
Iris.warn("=");
|
||||||
|
Iris.warn("Iris is not compatible with this version of Minecraft.\nPlease use " + NMSBinding1_20_1.NMS_VERSION + " or use an older version of Iris.");
|
||||||
|
Iris.warn("=");
|
||||||
|
Iris.warn("=");
|
||||||
|
Iris.warn("=");
|
||||||
|
Iris.warn("============================================");
|
||||||
|
}
|
||||||
|
if (!instance.getServer().getVersion().contains("Purpur")) {
|
||||||
|
passed = false;
|
||||||
|
Iris.info("We recommend using Purpur for the best experience with Iris.");
|
||||||
|
Iris.info("Purpur is a fork of Paper that is optimized for performance and stability.");
|
||||||
|
Iris.info("Plugins that work on Spigot / Paper work on Purpur.");
|
||||||
|
Iris.info("You can download it here: https://purpurmc.org");
|
||||||
|
}
|
||||||
|
return passed;
|
||||||
|
}
|
||||||
|
|
||||||
private void checkConfigHotload() {
|
private void checkConfigHotload() {
|
||||||
if(configWatcher.checkModified()) {
|
if (configWatcher.checkModified()) {
|
||||||
IrisSettings.invalidate();
|
IrisSettings.invalidate();
|
||||||
IrisSettings.get();
|
IrisSettings.get();
|
||||||
configWatcher.checkModified();
|
configWatcher.checkModified();
|
||||||
@@ -571,17 +611,17 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void tickQueue() {
|
private void tickQueue() {
|
||||||
synchronized(Iris.syncJobs) {
|
synchronized (Iris.syncJobs) {
|
||||||
if(!Iris.syncJobs.hasNext()) {
|
if (!Iris.syncJobs.hasNext()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
long ms = M.ms();
|
long ms = M.ms();
|
||||||
|
|
||||||
while(Iris.syncJobs.hasNext() && M.ms() - ms < 25) {
|
while (Iris.syncJobs.hasNext() && M.ms() - ms < 25) {
|
||||||
try {
|
try {
|
||||||
Iris.syncJobs.next().run();
|
Iris.syncJobs.next().run();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
@@ -590,7 +630,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void bstats() {
|
private void bstats() {
|
||||||
if(IrisSettings.get().getGeneral().isPluginMetrics()) {
|
if (IrisSettings.get().getGeneral().isPluginMetrics()) {
|
||||||
J.s(() -> new Metrics(Iris.instance, 8757));
|
J.s(() -> new Metrics(Iris.instance, 8757));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -614,12 +654,12 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
@Override
|
@Override
|
||||||
public ChunkGenerator getDefaultWorldGenerator(String worldName, String id) {
|
public ChunkGenerator getDefaultWorldGenerator(String worldName, String id) {
|
||||||
Iris.debug("Default World Generator Called for " + worldName + " using ID: " + id);
|
Iris.debug("Default World Generator Called for " + worldName + " using ID: " + id);
|
||||||
if(worldName.equals("test")) {
|
if (worldName.equals("test")) {
|
||||||
try {
|
try {
|
||||||
throw new RuntimeException();
|
throw new RuntimeException();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.info(e.getStackTrace()[1].getClassName());
|
Iris.info(e.getStackTrace()[1].getClassName());
|
||||||
if(e.getStackTrace()[1].getClassName().contains("com.onarandombox.MultiverseCore")) {
|
if (e.getStackTrace()[1].getClassName().contains("com.onarandombox.MultiverseCore")) {
|
||||||
Iris.debug("MVC Test detected, Quick! Send them the dummy!");
|
Iris.debug("MVC Test detected, Quick! Send them the dummy!");
|
||||||
return new DummyChunkGenerator();
|
return new DummyChunkGenerator();
|
||||||
}
|
}
|
||||||
@@ -627,20 +667,20 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
IrisDimension dim;
|
IrisDimension dim;
|
||||||
if(id == null || id.isEmpty()) {
|
if (id == null || id.isEmpty()) {
|
||||||
dim = IrisData.loadAnyDimension(IrisSettings.get().getGenerator().getDefaultWorldType());
|
dim = IrisData.loadAnyDimension(IrisSettings.get().getGenerator().getDefaultWorldType());
|
||||||
} else {
|
} else {
|
||||||
dim = IrisData.loadAnyDimension(id);
|
dim = IrisData.loadAnyDimension(id);
|
||||||
}
|
}
|
||||||
Iris.debug("Generator ID: " + id + " requested by bukkit/plugin");
|
Iris.debug("Generator ID: " + id + " requested by bukkit/plugin");
|
||||||
|
|
||||||
if(dim == null) {
|
if (dim == null) {
|
||||||
Iris.warn("Unable to find dimension type " + id + " Looking for online packs...");
|
Iris.warn("Unable to find dimension type " + id + " Looking for online packs...");
|
||||||
|
|
||||||
service(StudioSVC.class).downloadSearch(new VolmitSender(Bukkit.getConsoleSender()), id, true);
|
service(StudioSVC.class).downloadSearch(new VolmitSender(Bukkit.getConsoleSender()), id, true);
|
||||||
dim = IrisData.loadAnyDimension(id);
|
dim = IrisData.loadAnyDimension(id);
|
||||||
|
|
||||||
if(dim == null) {
|
if (dim == null) {
|
||||||
throw new RuntimeException("Can't find dimension " + id + "!");
|
throw new RuntimeException("Can't find dimension " + id + "!");
|
||||||
} else {
|
} else {
|
||||||
Iris.info("Resolved missing dimension, proceeding with generation.");
|
Iris.info("Resolved missing dimension, proceeding with generation.");
|
||||||
@@ -650,18 +690,18 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
Iris.debug("Assuming IrisDimension: " + dim.getName());
|
Iris.debug("Assuming IrisDimension: " + dim.getName());
|
||||||
|
|
||||||
IrisWorld w = IrisWorld.builder()
|
IrisWorld w = IrisWorld.builder()
|
||||||
.name(worldName)
|
.name(worldName)
|
||||||
.seed(1337)
|
.seed(1337)
|
||||||
.environment(dim.getEnvironment())
|
.environment(dim.getEnvironment())
|
||||||
.worldFolder(new File(worldName))
|
.worldFolder(new File(Bukkit.getWorldContainer(), worldName))
|
||||||
.minHeight(dim.getMinHeight())
|
.minHeight(dim.getMinHeight())
|
||||||
.maxHeight(dim.getMaxHeight())
|
.maxHeight(dim.getMaxHeight())
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
Iris.debug("Generator Config: " + w.toString());
|
Iris.debug("Generator Config: " + w.toString());
|
||||||
|
|
||||||
File ff = new File(w.worldFolder(), "iris/pack");
|
File ff = new File(w.worldFolder(), "iris/pack");
|
||||||
if(!ff.exists() || ff.listFiles().length == 0) {
|
if (!ff.exists() || ff.listFiles().length == 0) {
|
||||||
ff.mkdirs();
|
ff.mkdirs();
|
||||||
service(StudioSVC.class).installIntoWorld(sender, dim.getLoadKey(), ff.getParentFile());
|
service(StudioSVC.class).installIntoWorld(sender, dim.getLoadKey(), ff.getParentFile());
|
||||||
}
|
}
|
||||||
@@ -670,7 +710,7 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void splash() {
|
public void splash() {
|
||||||
if(!IrisSettings.get().getGeneral().isSplashLogoStartup()) {
|
if (!IrisSettings.get().getGeneral().isSplashLogoStartup()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -697,9 +737,10 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
Iris.info("Bukkit version: " + Bukkit.getBukkitVersion());
|
Iris.info("Bukkit version: " + Bukkit.getBukkitVersion());
|
||||||
Iris.info("Java version: " + getJavaVersion());
|
Iris.info("Java version: " + getJavaVersion());
|
||||||
Iris.info("Custom Biomes: " + INMS.get().countCustomBiomes());
|
Iris.info("Custom Biomes: " + INMS.get().countCustomBiomes());
|
||||||
|
setupChecks();
|
||||||
printPacks();
|
printPacks();
|
||||||
|
|
||||||
for(int i = 0; i < info.length; i++) {
|
for (int i = 0; i < info.length; i++) {
|
||||||
splash[i] += info[i];
|
splash[i] += info[i];
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -709,21 +750,22 @@ public class Iris extends VolmitPlugin implements Listener {
|
|||||||
private void printPacks() {
|
private void printPacks() {
|
||||||
File packFolder = Iris.service(StudioSVC.class).getWorkspaceFolder();
|
File packFolder = Iris.service(StudioSVC.class).getWorkspaceFolder();
|
||||||
File[] packs = packFolder.listFiles(File::isDirectory);
|
File[] packs = packFolder.listFiles(File::isDirectory);
|
||||||
if(packs == null || packs.length == 0)
|
if (packs == null || packs.length == 0)
|
||||||
return;
|
return;
|
||||||
Iris.info("Custom Dimensions: " + packs.length);
|
Iris.info("Custom Dimensions: " + packs.length);
|
||||||
for(File f : packs)
|
for (File f : packs)
|
||||||
printPack(f);
|
printPack(f);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void printPack(File pack) {
|
private void printPack(File pack) {
|
||||||
String dimName = pack.getName();
|
String dimName = pack.getName();
|
||||||
String version = "???";
|
String version = "???";
|
||||||
try(FileReader r = new FileReader(new File(pack, "dimensions/" + dimName + ".json"))) {
|
try (FileReader r = new FileReader(new File(pack, "dimensions/" + dimName + ".json"))) {
|
||||||
JsonObject json = JsonParser.parseReader(r).getAsJsonObject();
|
JsonObject json = JsonParser.parseReader(r).getAsJsonObject();
|
||||||
if(json.has("version"))
|
if (json.has("version"))
|
||||||
version = json.get("version").getAsString();
|
version = json.get("version").getAsString();
|
||||||
} catch(IOException | JsonParseException ignored) { }
|
} catch (IOException | JsonParseException ignored) {
|
||||||
|
}
|
||||||
Iris.info(" " + dimName + " v" + version);
|
Iris.info(" " + dimName + " v" + version);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -43,13 +43,64 @@ public class IrisSettings {
|
|||||||
private IrisSettingsPerformance performance = new IrisSettingsPerformance();
|
private IrisSettingsPerformance performance = new IrisSettingsPerformance();
|
||||||
|
|
||||||
public static int getThreadCount(int c) {
|
public static int getThreadCount(int c) {
|
||||||
return switch(c) {
|
return switch (c) {
|
||||||
case -1, -2, -4 -> Runtime.getRuntime().availableProcessors() / -c;
|
case -1, -2, -4 -> Runtime.getRuntime().availableProcessors() / -c;
|
||||||
case 0, 1, 2 -> 1;
|
case 0, 1, 2 -> 1;
|
||||||
default -> Math.max(c, 2);
|
default -> Math.max(c, 2);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static IrisSettings get() {
|
||||||
|
if (settings != null) {
|
||||||
|
return settings;
|
||||||
|
}
|
||||||
|
|
||||||
|
settings = new IrisSettings();
|
||||||
|
|
||||||
|
File s = Iris.instance.getDataFile("settings.json");
|
||||||
|
|
||||||
|
if (!s.exists()) {
|
||||||
|
try {
|
||||||
|
IO.writeAll(s, new JSONObject(new Gson().toJson(settings)).toString(4));
|
||||||
|
} catch (JSONException | IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
Iris.reportError(e);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
String ss = IO.readAll(s);
|
||||||
|
settings = new Gson().fromJson(ss, IrisSettings.class);
|
||||||
|
try {
|
||||||
|
IO.writeAll(s, new JSONObject(new Gson().toJson(settings)).toString(4));
|
||||||
|
} catch (IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
} catch (Throwable ee) {
|
||||||
|
// Iris.reportError(ee); causes a self-reference & stackoverflow
|
||||||
|
Iris.error("Configuration Error in settings.json! " + ee.getClass().getSimpleName() + ": " + ee.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return settings;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void invalidate() {
|
||||||
|
synchronized (settings) {
|
||||||
|
settings = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void forceSave() {
|
||||||
|
File s = Iris.instance.getDataFile("settings.json");
|
||||||
|
|
||||||
|
try {
|
||||||
|
IO.writeAll(s, new JSONObject(new Gson().toJson(settings)).toString(4));
|
||||||
|
} catch (JSONException | IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
Iris.reportError(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Data
|
@Data
|
||||||
public static class IrisSettingsAutoconfiguration {
|
public static class IrisSettingsAutoconfiguration {
|
||||||
public boolean configureSpigotTimeoutTime = true;
|
public boolean configureSpigotTimeoutTime = true;
|
||||||
@@ -105,6 +156,8 @@ public class IrisSettings {
|
|||||||
public int spinh = -20;
|
public int spinh = -20;
|
||||||
public int spins = 7;
|
public int spins = 7;
|
||||||
public int spinb = 8;
|
public int spinb = 8;
|
||||||
|
public String cartographerMessage = "Iris does not allow cartographers in its world due to crashes.";
|
||||||
|
|
||||||
|
|
||||||
@SuppressWarnings("BooleanMethodIsAlwaysInverted")
|
@SuppressWarnings("BooleanMethodIsAlwaysInverted")
|
||||||
public boolean canUseCustomColors(VolmitSender volmitSender) {
|
public boolean canUseCustomColors(VolmitSender volmitSender) {
|
||||||
@@ -132,55 +185,4 @@ public class IrisSettings {
|
|||||||
public boolean disableTimeAndWeather = true;
|
public boolean disableTimeAndWeather = true;
|
||||||
public boolean autoStartDefaultStudio = false;
|
public boolean autoStartDefaultStudio = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static IrisSettings get() {
|
|
||||||
if(settings != null) {
|
|
||||||
return settings;
|
|
||||||
}
|
|
||||||
|
|
||||||
settings = new IrisSettings();
|
|
||||||
|
|
||||||
File s = Iris.instance.getDataFile("settings.json");
|
|
||||||
|
|
||||||
if(!s.exists()) {
|
|
||||||
try {
|
|
||||||
IO.writeAll(s, new JSONObject(new Gson().toJson(settings)).toString(4));
|
|
||||||
} catch(JSONException | IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
Iris.reportError(e);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
try {
|
|
||||||
String ss = IO.readAll(s);
|
|
||||||
settings = new Gson().fromJson(ss, IrisSettings.class);
|
|
||||||
try {
|
|
||||||
IO.writeAll(s, new JSONObject(new Gson().toJson(settings)).toString(4));
|
|
||||||
} catch(IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
} catch(Throwable ee) {
|
|
||||||
// Iris.reportError(ee); causes a self-reference & stackoverflow
|
|
||||||
Iris.error("Configuration Error in settings.json! " + ee.getClass().getSimpleName() + ": " + ee.getMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return settings;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void invalidate() {
|
|
||||||
synchronized(settings) {
|
|
||||||
settings = null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void forceSave() {
|
|
||||||
File s = Iris.instance.getDataFile("settings.json");
|
|
||||||
|
|
||||||
try {
|
|
||||||
IO.writeAll(s, new JSONObject(new Gson().toJson(settings)).toString(4));
|
|
||||||
} catch(JSONException | IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
Iris.reportError(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -27,7 +27,6 @@ import com.volmit.iris.engine.object.IrisDimension;
|
|||||||
import com.volmit.iris.util.collection.KList;
|
import com.volmit.iris.util.collection.KList;
|
||||||
import com.volmit.iris.util.collection.KSet;
|
import com.volmit.iris.util.collection.KSet;
|
||||||
import com.volmit.iris.util.format.C;
|
import com.volmit.iris.util.format.C;
|
||||||
import com.volmit.iris.util.io.IO;
|
|
||||||
import com.volmit.iris.util.plugin.VolmitSender;
|
import com.volmit.iris.util.plugin.VolmitSender;
|
||||||
import com.volmit.iris.util.scheduling.J;
|
import com.volmit.iris.util.scheduling.J;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
@@ -38,16 +37,17 @@ import org.bukkit.entity.Player;
|
|||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.util.List;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
public class ServerConfigurator {
|
public class ServerConfigurator {
|
||||||
public static void configure() {
|
public static void configure() {
|
||||||
IrisSettings.IrisSettingsAutoconfiguration s = IrisSettings.get().getAutoConfiguration();
|
IrisSettings.IrisSettingsAutoconfiguration s = IrisSettings.get().getAutoConfiguration();
|
||||||
if(s.isConfigureSpigotTimeoutTime()) {
|
if (s.isConfigureSpigotTimeoutTime()) {
|
||||||
J.attempt(ServerConfigurator::increaseKeepAliveSpigot);
|
J.attempt(ServerConfigurator::increaseKeepAliveSpigot);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(s.isConfigurePaperWatchdogDelay()) {
|
if (s.isConfigurePaperWatchdogDelay()) {
|
||||||
J.attempt(ServerConfigurator::increasePaperWatchdog);
|
J.attempt(ServerConfigurator::increasePaperWatchdog);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -60,7 +60,7 @@ public class ServerConfigurator {
|
|||||||
f.load(spigotConfig);
|
f.load(spigotConfig);
|
||||||
long tt = f.getLong("settings.timeout-time");
|
long tt = f.getLong("settings.timeout-time");
|
||||||
|
|
||||||
if(tt < TimeUnit.MINUTES.toSeconds(5)) {
|
if (tt < TimeUnit.MINUTES.toSeconds(5)) {
|
||||||
Iris.warn("Updating spigot.yml timeout-time: " + tt + " -> " + TimeUnit.MINUTES.toSeconds(5) + " (5 minutes)");
|
Iris.warn("Updating spigot.yml timeout-time: " + tt + " -> " + TimeUnit.MINUTES.toSeconds(5) + " (5 minutes)");
|
||||||
Iris.warn("You can disable this change (autoconfigureServer) in Iris settings, then change back the value.");
|
Iris.warn("You can disable this change (autoconfigureServer) in Iris settings, then change back the value.");
|
||||||
f.set("settings.timeout-time", TimeUnit.MINUTES.toSeconds(5));
|
f.set("settings.timeout-time", TimeUnit.MINUTES.toSeconds(5));
|
||||||
@@ -74,7 +74,7 @@ public class ServerConfigurator {
|
|||||||
f.load(spigotConfig);
|
f.load(spigotConfig);
|
||||||
long tt = f.getLong("watchdog.early-warning-delay");
|
long tt = f.getLong("watchdog.early-warning-delay");
|
||||||
|
|
||||||
if(tt < TimeUnit.MINUTES.toMillis(3)) {
|
if (tt < TimeUnit.MINUTES.toMillis(3)) {
|
||||||
Iris.warn("Updating paper.yml watchdog early-warning-delay: " + tt + " -> " + TimeUnit.MINUTES.toMillis(3) + " (3 minutes)");
|
Iris.warn("Updating paper.yml watchdog early-warning-delay: " + tt + " -> " + TimeUnit.MINUTES.toMillis(3) + " (3 minutes)");
|
||||||
Iris.warn("You can disable this change (autoconfigureServer) in Iris settings, then change back the value.");
|
Iris.warn("You can disable this change (autoconfigureServer) in Iris settings, then change back the value.");
|
||||||
f.set("watchdog.early-warning-delay", TimeUnit.MINUTES.toMillis(3));
|
f.set("watchdog.early-warning-delay", TimeUnit.MINUTES.toMillis(3));
|
||||||
@@ -82,61 +82,39 @@ public class ServerConfigurator {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static File getDatapacksFolder() {
|
private static List<File> getDatapacksFolder() {
|
||||||
if(!IrisSettings.get().getGeneral().forceMainWorld.isEmpty()) {
|
if (!IrisSettings.get().getGeneral().forceMainWorld.isEmpty()) {
|
||||||
return new File(IrisSettings.get().getGeneral().forceMainWorld + "/datapacks");
|
return new KList<File>().qadd(new File(Bukkit.getWorldContainer(), IrisSettings.get().getGeneral().forceMainWorld + "/datapacks"));
|
||||||
}
|
}
|
||||||
|
KList<File> worlds = new KList<>();
|
||||||
File props = new File("server.properties");
|
Bukkit.getServer().getWorlds().forEach(w -> worlds.add(new File(w.getWorldFolder(), "datapacks")));
|
||||||
|
return worlds;
|
||||||
if(props.exists()) {
|
|
||||||
try {
|
|
||||||
KList<String> m = new KList<>(IO.readAll(props).split("\\Q\n\\E"));
|
|
||||||
|
|
||||||
for(String i : m) {
|
|
||||||
if(i.trim().startsWith("level-name=")) {
|
|
||||||
return new File(i.trim().split("\\Q=\\E")[1] + "/datapacks");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch(IOException e) {
|
|
||||||
Iris.reportError(e);
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public static void installDataPacks(boolean fullInstall) {
|
public static void installDataPacks(boolean fullInstall) {
|
||||||
Iris.info("Checking Data Packs...");
|
Iris.info("Checking Data Packs...");
|
||||||
boolean reboot = false;
|
|
||||||
File packs = new File("plugins/Iris/packs");
|
File packs = new File("plugins/Iris/packs");
|
||||||
File dpacks = getDatapacksFolder();
|
|
||||||
|
|
||||||
if(dpacks == null) {
|
if (packs.exists()) {
|
||||||
Iris.error("Cannot find the datapacks folder! Please try generating a default world first maybe? Is this a new server?");
|
for (File i : packs.listFiles()) {
|
||||||
return;
|
if (i.isDirectory()) {
|
||||||
}
|
|
||||||
|
|
||||||
if(packs.exists()) {
|
|
||||||
for(File i : packs.listFiles()) {
|
|
||||||
if(i.isDirectory()) {
|
|
||||||
Iris.verbose("Checking Pack: " + i.getPath());
|
Iris.verbose("Checking Pack: " + i.getPath());
|
||||||
IrisData data = IrisData.get(i);
|
IrisData data = IrisData.get(i);
|
||||||
File dims = new File(i, "dimensions");
|
File dims = new File(i, "dimensions");
|
||||||
|
|
||||||
if(dims.exists()) {
|
if (dims.exists()) {
|
||||||
for(File j : dims.listFiles()) {
|
for (File j : dims.listFiles()) {
|
||||||
if(j.getName().endsWith(".json")) {
|
if (j.getName().endsWith(".json")) {
|
||||||
IrisDimension dim = data.getDimensionLoader().load(j.getName().split("\\Q.\\E")[0]);
|
IrisDimension dim = data.getDimensionLoader().load(j.getName().split("\\Q.\\E")[0]);
|
||||||
|
|
||||||
if(dim == null) {
|
if (dim == null) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iris.verbose(" Checking Dimension " + dim.getLoadFile().getPath());
|
Iris.verbose(" Checking Dimension " + dim.getLoadFile().getPath());
|
||||||
if(dim.installDataPack(() -> data, dpacks)) {
|
for (File dpack : getDatapacksFolder()) {
|
||||||
reboot = true;
|
dim.installDataPack(() -> data, dpack);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -147,39 +125,32 @@ public class ServerConfigurator {
|
|||||||
|
|
||||||
Iris.info("Data Packs Setup!");
|
Iris.info("Data Packs Setup!");
|
||||||
|
|
||||||
if(fullInstall) {
|
if (fullInstall)
|
||||||
verifyDataPacksPost(IrisSettings.get().getAutoConfiguration().isAutoRestartOnCustomBiomeInstall());
|
verifyDataPacksPost(IrisSettings.get().getAutoConfiguration().isAutoRestartOnCustomBiomeInstall());
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void verifyDataPacksPost(boolean allowRestarting) {
|
private static void verifyDataPacksPost(boolean allowRestarting) {
|
||||||
File packs = new File("plugins/Iris/packs");
|
File packs = new File("plugins/Iris/packs");
|
||||||
File dpacks = getDatapacksFolder();
|
|
||||||
|
|
||||||
if(dpacks == null) {
|
|
||||||
Iris.error("Cannot find the datapacks folder! Please try generating a default world first maybe? Is this a new server?");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean bad = false;
|
boolean bad = false;
|
||||||
if(packs.exists()) {
|
if (packs.exists()) {
|
||||||
for(File i : packs.listFiles()) {
|
for (File i : packs.listFiles()) {
|
||||||
if(i.isDirectory()) {
|
if (i.isDirectory()) {
|
||||||
Iris.verbose("Checking Pack: " + i.getPath());
|
Iris.verbose("Checking Pack: " + i.getPath());
|
||||||
IrisData data = IrisData.get(i);
|
IrisData data = IrisData.get(i);
|
||||||
File dims = new File(i, "dimensions");
|
File dims = new File(i, "dimensions");
|
||||||
|
|
||||||
if(dims.exists()) {
|
if (dims.exists()) {
|
||||||
for(File j : dims.listFiles()) {
|
for (File j : dims.listFiles()) {
|
||||||
if(j.getName().endsWith(".json")) {
|
if (j.getName().endsWith(".json")) {
|
||||||
IrisDimension dim = data.getDimensionLoader().load(j.getName().split("\\Q.\\E")[0]);
|
IrisDimension dim = data.getDimensionLoader().load(j.getName().split("\\Q.\\E")[0]);
|
||||||
|
|
||||||
if(dim == null) {
|
if (dim == null) {
|
||||||
Iris.error("Failed to load " + j.getPath() + " ");
|
Iris.error("Failed to load " + j.getPath() + " ");
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!verifyDataPackInstalled(dim)) {
|
if (!verifyDataPackInstalled(dim)) {
|
||||||
bad = true;
|
bad = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -189,10 +160,10 @@ public class ServerConfigurator {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(bad) {
|
if (bad) {
|
||||||
if(allowRestarting) {
|
if (allowRestarting) {
|
||||||
restart();
|
restart();
|
||||||
} else if(INMS.get().supportsDataPacks()) {
|
} else if (INMS.get().supportsDataPacks()) {
|
||||||
Iris.error("============================================================================");
|
Iris.error("============================================================================");
|
||||||
Iris.error(C.ITALIC + "You need to restart your server to properly generate custom biomes.");
|
Iris.error(C.ITALIC + "You need to restart your server to properly generate custom biomes.");
|
||||||
Iris.error(C.ITALIC + "By continuing, Iris will use backup biomes in place of the custom biomes.");
|
Iris.error(C.ITALIC + "By continuing, Iris will use backup biomes in place of the custom biomes.");
|
||||||
@@ -200,8 +171,8 @@ public class ServerConfigurator {
|
|||||||
Iris.error(C.UNDERLINE + "IT IS HIGHLY RECOMMENDED YOU RESTART THE SERVER BEFORE GENERATING!");
|
Iris.error(C.UNDERLINE + "IT IS HIGHLY RECOMMENDED YOU RESTART THE SERVER BEFORE GENERATING!");
|
||||||
Iris.error("============================================================================");
|
Iris.error("============================================================================");
|
||||||
|
|
||||||
for(Player i : Bukkit.getOnlinePlayers()) {
|
for (Player i : Bukkit.getOnlinePlayers()) {
|
||||||
if(i.isOp() || i.hasPermission("iris.all")) {
|
if (i.isOp() || i.hasPermission("iris.all")) {
|
||||||
VolmitSender sender = new VolmitSender(i, Iris.instance.getTag("WARNING"));
|
VolmitSender sender = new VolmitSender(i, Iris.instance.getTag("WARNING"));
|
||||||
sender.sendMessage("There are some Iris Packs that have custom biomes in them");
|
sender.sendMessage("There are some Iris Packs that have custom biomes in them");
|
||||||
sender.sendMessage("You need to restart your server to use these packs.");
|
sender.sendMessage("You need to restart your server to use these packs.");
|
||||||
@@ -231,16 +202,16 @@ public class ServerConfigurator {
|
|||||||
KSet<String> keys = new KSet<>();
|
KSet<String> keys = new KSet<>();
|
||||||
boolean warn = false;
|
boolean warn = false;
|
||||||
|
|
||||||
for(IrisBiome i : dimension.getAllBiomes(() -> idm)) {
|
for (IrisBiome i : dimension.getAllBiomes(() -> idm)) {
|
||||||
if(i.isCustom()) {
|
if (i.isCustom()) {
|
||||||
for(IrisBiomeCustom j : i.getCustomDerivitives()) {
|
for (IrisBiomeCustom j : i.getCustomDerivitives()) {
|
||||||
keys.add(dimension.getLoadKey() + ":" + j.getId());
|
keys.add(dimension.getLoadKey() + ":" + j.getId());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!INMS.get().supportsDataPacks()) {
|
if (!INMS.get().supportsDataPacks()) {
|
||||||
if(!keys.isEmpty()) {
|
if (!keys.isEmpty()) {
|
||||||
Iris.warn("===================================================================================");
|
Iris.warn("===================================================================================");
|
||||||
Iris.warn("Pack " + dimension.getLoadKey() + " has " + keys.size() + " custom biome(s). ");
|
Iris.warn("Pack " + dimension.getLoadKey() + " has " + keys.size() + " custom biome(s). ");
|
||||||
Iris.warn("Your server version does not yet support datapacks for iris.");
|
Iris.warn("Your server version does not yet support datapacks for iris.");
|
||||||
@@ -251,16 +222,16 @@ public class ServerConfigurator {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
for(String i : keys) {
|
for (String i : keys) {
|
||||||
Object o = INMS.get().getCustomBiomeBaseFor(i);
|
Object o = INMS.get().getCustomBiomeBaseFor(i);
|
||||||
|
|
||||||
if(o == null) {
|
if (o == null) {
|
||||||
Iris.warn("The Biome " + i + " is not registered on the server.");
|
Iris.warn("The Biome " + i + " is not registered on the server.");
|
||||||
warn = true;
|
warn = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(warn) {
|
if (warn) {
|
||||||
Iris.error("The Pack " + dimension.getLoadKey() + " is INCAPABLE of generating custom biomes");
|
Iris.error("The Pack " + dimension.getLoadKey() + " is INCAPABLE of generating custom biomes");
|
||||||
Iris.error("If not done automatically, restart your server before generating with this pack!");
|
Iris.error("If not done automatically, restart your server before generating with this pack!");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,35 +20,29 @@ package com.volmit.iris.core.commands;
|
|||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.service.StudioSVC;
|
import com.volmit.iris.core.service.StudioSVC;
|
||||||
import com.volmit.iris.engine.object.IrisBiome;
|
import com.volmit.iris.engine.object.*;
|
||||||
import com.volmit.iris.engine.object.IrisCave;
|
|
||||||
import com.volmit.iris.engine.object.IrisDimension;
|
|
||||||
import com.volmit.iris.engine.object.IrisJigsawPiece;
|
|
||||||
import com.volmit.iris.engine.object.IrisJigsawPool;
|
|
||||||
import com.volmit.iris.engine.object.IrisJigsawStructure;
|
|
||||||
import com.volmit.iris.engine.object.IrisRegion;
|
|
||||||
import com.volmit.iris.util.decree.DecreeExecutor;
|
import com.volmit.iris.util.decree.DecreeExecutor;
|
||||||
import com.volmit.iris.util.decree.DecreeOrigin;
|
import com.volmit.iris.util.decree.DecreeOrigin;
|
||||||
import com.volmit.iris.util.decree.annotations.Decree;
|
import com.volmit.iris.util.decree.annotations.Decree;
|
||||||
import com.volmit.iris.util.decree.annotations.Param;
|
import com.volmit.iris.util.decree.annotations.Param;
|
||||||
import com.volmit.iris.util.format.C;
|
import com.volmit.iris.util.format.C;
|
||||||
|
|
||||||
import java.awt.Desktop;
|
import java.awt.*;
|
||||||
|
|
||||||
|
|
||||||
@Decree(name = "edit", origin = DecreeOrigin.PLAYER, studio = true, description = "Edit something")
|
@Decree(name = "edit", origin = DecreeOrigin.PLAYER, studio = true, description = "Edit something")
|
||||||
public class CommandEdit implements DecreeExecutor {
|
public class CommandEdit implements DecreeExecutor {
|
||||||
|
|
||||||
private boolean noStudio() {
|
private boolean noStudio() {
|
||||||
if(!sender().isPlayer()) {
|
if (!sender().isPlayer()) {
|
||||||
sender().sendMessage(C.RED + "Players only!");
|
sender().sendMessage(C.RED + "Players only!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if(!Iris.service(StudioSVC.class).isProjectOpen()) {
|
if (!Iris.service(StudioSVC.class).isProjectOpen()) {
|
||||||
sender().sendMessage(C.RED + "No studio world is open!");
|
sender().sendMessage(C.RED + "No studio world is open!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if(!engine().isStudio()) {
|
if (!engine().isStudio()) {
|
||||||
sender().sendMessage(C.RED + "You must be in a studio world!");
|
sender().sendMessage(C.RED + "You must be in a studio world!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -58,17 +52,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the biome you specified", aliases = {"b"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the biome you specified", aliases = {"b"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void biome(@Param(contextual = false, description = "The biome to edit") IrisBiome biome) {
|
public void biome(@Param(contextual = false, description = "The biome to edit") IrisBiome biome) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(biome == null || biome.getLoadFile() == null) {
|
if (biome == null || biome.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(biome.getLoadFile());
|
Desktop.getDesktop().open(biome.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + biome.getTypeName() + " " + biome.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + biome.getTypeName() + " " + biome.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
@@ -76,17 +70,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the region you specified", aliases = {"r"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the region you specified", aliases = {"r"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void region(@Param(contextual = false, description = "The region to edit") IrisRegion region) {
|
public void region(@Param(contextual = false, description = "The region to edit") IrisRegion region) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(region == null || region.getLoadFile() == null) {
|
if (region == null || region.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(region.getLoadFile());
|
Desktop.getDesktop().open(region.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + region.getTypeName() + " " + region.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + region.getTypeName() + " " + region.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
@@ -94,17 +88,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the dimension you specified", aliases = {"d"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the dimension you specified", aliases = {"d"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void dimension(@Param(contextual = false, description = "The dimension to edit") IrisDimension dimension) {
|
public void dimension(@Param(contextual = false, description = "The dimension to edit") IrisDimension dimension) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(dimension == null || dimension.getLoadFile() == null) {
|
if (dimension == null || dimension.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(dimension.getLoadFile());
|
Desktop.getDesktop().open(dimension.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + dimension.getTypeName() + " " + dimension.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + dimension.getTypeName() + " " + dimension.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
@@ -112,17 +106,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the cave file you specified", aliases = {"c"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the cave file you specified", aliases = {"c"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void cave(@Param(contextual = false, description = "The cave to edit") IrisCave cave) {
|
public void cave(@Param(contextual = false, description = "The cave to edit") IrisCave cave) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(cave == null || cave.getLoadFile() == null) {
|
if (cave == null || cave.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(cave.getLoadFile());
|
Desktop.getDesktop().open(cave.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + cave.getTypeName() + " " + cave.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + cave.getTypeName() + " " + cave.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
@@ -130,17 +124,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the structure file you specified", aliases = {"jigsawstructure", "structure"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the structure file you specified", aliases = {"jigsawstructure", "structure"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void jigsaw(@Param(contextual = false, description = "The jigsaw structure to edit") IrisJigsawStructure jigsaw) {
|
public void jigsaw(@Param(contextual = false, description = "The jigsaw structure to edit") IrisJigsawStructure jigsaw) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(jigsaw == null || jigsaw.getLoadFile() == null) {
|
if (jigsaw == null || jigsaw.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(jigsaw.getLoadFile());
|
Desktop.getDesktop().open(jigsaw.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + jigsaw.getTypeName() + " " + jigsaw.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + jigsaw.getTypeName() + " " + jigsaw.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
@@ -148,17 +142,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the pool file you specified", aliases = {"jigsawpool", "pool"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the pool file you specified", aliases = {"jigsawpool", "pool"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void jigsawPool(@Param(contextual = false, description = "The jigsaw pool to edit") IrisJigsawPool pool) {
|
public void jigsawPool(@Param(contextual = false, description = "The jigsaw pool to edit") IrisJigsawPool pool) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(pool == null || pool.getLoadFile() == null) {
|
if (pool == null || pool.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(pool.getLoadFile());
|
Desktop.getDesktop().open(pool.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + pool.getTypeName() + " " + pool.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + pool.getTypeName() + " " + pool.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
@@ -166,17 +160,17 @@ public class CommandEdit implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Edit the jigsaw piece file you specified", aliases = {"jigsawpiece", "piece"}, origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Edit the jigsaw piece file you specified", aliases = {"jigsawpiece", "piece"}, origin = DecreeOrigin.PLAYER)
|
||||||
public void jigsawPiece(@Param(contextual = false, description = "The jigsaw piece to edit") IrisJigsawPiece piece) {
|
public void jigsawPiece(@Param(contextual = false, description = "The jigsaw piece to edit") IrisJigsawPiece piece) {
|
||||||
if(noStudio()) {
|
if (noStudio()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
if(piece == null || piece.getLoadFile() == null) {
|
if (piece == null || piece.getLoadFile() == null) {
|
||||||
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
sender().sendMessage(C.GOLD + "Cannot find the file; Perhaps it was not loaded directly from a file?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Desktop.getDesktop().open(piece.getLoadFile());
|
Desktop.getDesktop().open(piece.getLoadFile());
|
||||||
sender().sendMessage(C.GREEN + "Opening " + piece.getTypeName() + " " + piece.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
sender().sendMessage(C.GREEN + "Opening " + piece.getTypeName() + " " + piece.getLoadFile().getName().split("\\Q.\\E")[0] + " in VSCode! ");
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
sender().sendMessage(C.RED + "Cant find the file. Or registrant does not exist");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,12 +33,12 @@ import com.volmit.iris.util.format.C;
|
|||||||
public class CommandFind implements DecreeExecutor {
|
public class CommandFind implements DecreeExecutor {
|
||||||
@Decree(description = "Find a biome")
|
@Decree(description = "Find a biome")
|
||||||
public void biome(
|
public void biome(
|
||||||
@Param(description = "The biome to look for")
|
@Param(description = "The biome to look for")
|
||||||
IrisBiome biome
|
IrisBiome biome
|
||||||
) {
|
) {
|
||||||
Engine e = engine();
|
Engine e = engine();
|
||||||
|
|
||||||
if(e == null) {
|
if (e == null) {
|
||||||
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -48,12 +48,12 @@ public class CommandFind implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Find a region")
|
@Decree(description = "Find a region")
|
||||||
public void region(
|
public void region(
|
||||||
@Param(description = "The region to look for")
|
@Param(description = "The region to look for")
|
||||||
IrisRegion region
|
IrisRegion region
|
||||||
) {
|
) {
|
||||||
Engine e = engine();
|
Engine e = engine();
|
||||||
|
|
||||||
if(e == null) {
|
if (e == null) {
|
||||||
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -63,12 +63,12 @@ public class CommandFind implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Find a structure")
|
@Decree(description = "Find a structure")
|
||||||
public void structure(
|
public void structure(
|
||||||
@Param(description = "The structure to look for")
|
@Param(description = "The structure to look for")
|
||||||
IrisJigsawStructure structure
|
IrisJigsawStructure structure
|
||||||
) {
|
) {
|
||||||
Engine e = engine();
|
Engine e = engine();
|
||||||
|
|
||||||
if(e == null) {
|
if (e == null) {
|
||||||
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -76,14 +76,28 @@ public class CommandFind implements DecreeExecutor {
|
|||||||
e.gotoJigsaw(structure, player());
|
e.gotoJigsaw(structure, player());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Decree(description = "Find a point of interest.")
|
||||||
|
public void poi(
|
||||||
|
@Param(description = "The type of PoI to look for.")
|
||||||
|
String type
|
||||||
|
) {
|
||||||
|
Engine e = engine();
|
||||||
|
if (e == null) {
|
||||||
|
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
e.gotoPOI(type, player());
|
||||||
|
}
|
||||||
|
|
||||||
@Decree(description = "Find an object")
|
@Decree(description = "Find an object")
|
||||||
public void object(
|
public void object(
|
||||||
@Param(description = "The object to look for", customHandler = ObjectHandler.class)
|
@Param(description = "The object to look for", customHandler = ObjectHandler.class)
|
||||||
String object
|
String object
|
||||||
) {
|
) {
|
||||||
Engine e = engine();
|
Engine e = engine();
|
||||||
|
|
||||||
if(e == null) {
|
if (e == null) {
|
||||||
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
sender().sendMessage(C.GOLD + "Not in an Iris World!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -38,10 +38,12 @@ import com.volmit.iris.util.parallel.MultiBurst;
|
|||||||
import com.volmit.iris.util.plugin.VolmitSender;
|
import com.volmit.iris.util.plugin.VolmitSender;
|
||||||
import com.volmit.iris.util.scheduling.J;
|
import com.volmit.iris.util.scheduling.J;
|
||||||
import com.volmit.iris.util.scheduling.jobs.QueueJob;
|
import com.volmit.iris.util.scheduling.jobs.QueueJob;
|
||||||
|
import org.bukkit.Bukkit;
|
||||||
import org.bukkit.Chunk;
|
import org.bukkit.Chunk;
|
||||||
import org.bukkit.World;
|
import org.bukkit.World;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
import java.util.concurrent.ExecutionException;
|
import java.util.concurrent.ExecutionException;
|
||||||
import java.util.concurrent.Future;
|
import java.util.concurrent.Future;
|
||||||
|
|
||||||
@@ -58,35 +60,33 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Create a new world", aliases = {"+", "c"})
|
@Decree(description = "Create a new world", aliases = {"+", "c"})
|
||||||
public void create(
|
public void create(
|
||||||
@Param(aliases = "world-name", description = "The name of the world to create")
|
@Param(aliases = "world-name", description = "The name of the world to create")
|
||||||
String name,
|
String name,
|
||||||
@Param(aliases = "dimension", description = "The dimension type to create the world with", defaultValue = "default")
|
@Param(aliases = "dimension", description = "The dimension type to create the world with", defaultValue = "default")
|
||||||
IrisDimension type,
|
IrisDimension type,
|
||||||
@Param(description = "The seed to generate the world with", defaultValue = "1337")
|
@Param(description = "The seed to generate the world with", defaultValue = "1337")
|
||||||
long seed
|
long seed
|
||||||
) {
|
) {
|
||||||
if(name.equals("iris")) {
|
if (name.equals("iris")) {
|
||||||
sender().sendMessage(C.RED + "You cannot use the world name \"iris\" for creating worlds as Iris uses this directory for studio worlds.");
|
sender().sendMessage(C.RED + "You cannot use the world name \"iris\" for creating worlds as Iris uses this directory for studio worlds.");
|
||||||
sender().sendMessage(C.RED + "May we suggest the name \"IrisWorld\" instead?");
|
sender().sendMessage(C.RED + "May we suggest the name \"IrisWorld\" instead?");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(new File(name).exists()) {
|
if (new File(Bukkit.getWorldContainer(), name).exists()) {
|
||||||
sender().sendMessage(C.RED + "That folder already exists!");
|
sender().sendMessage(C.RED + "That folder already exists!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
sender().sendMessage(C.RED + "You should not be using this command to create new worlds. Instead, use the tutorial: https://docs.volmit.com/iris/getting-started");
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
IrisToolbelt.createWorld()
|
IrisToolbelt.createWorld()
|
||||||
.dimension(type.getLoadKey())
|
.dimension(type.getLoadKey())
|
||||||
.name(name)
|
.name(name)
|
||||||
.seed(seed)
|
.seed(seed)
|
||||||
.sender(sender())
|
.sender(sender())
|
||||||
.studio(false)
|
.studio(false)
|
||||||
.create();
|
.create();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
sender().sendMessage(C.RED + "Exception raised during creation. See the console for more details.");
|
sender().sendMessage(C.RED + "Exception raised during creation. See the console for more details.");
|
||||||
Iris.error("Exception raised during world creation: " + e.getMessage());
|
Iris.error("Exception raised during world creation: " + e.getMessage());
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
@@ -96,6 +96,37 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
sender().sendMessage(C.GREEN + "Successfully created your world!");
|
sender().sendMessage(C.GREEN + "Successfully created your world!");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Decree(description = "Remove an Iris world", aliases = {"del", "rm"}, sync = true)
|
||||||
|
public void remove(
|
||||||
|
@Param(description = "The world to remove")
|
||||||
|
World world,
|
||||||
|
@Param(description = "Whether to also remove the folder (if set to false, just does not load the world)", defaultValue = "true")
|
||||||
|
boolean delete
|
||||||
|
) {
|
||||||
|
if (!IrisToolbelt.isIrisWorld(world)) {
|
||||||
|
sender().sendMessage(C.RED + "This is not an Iris world. Iris worlds: " + String.join(", ", Bukkit.getServer().getWorlds().stream().filter(IrisToolbelt::isIrisWorld).map(World::getName).toList()));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
sender().sendMessage(C.GREEN + "Removing world: " + world.getName());
|
||||||
|
try {
|
||||||
|
if (IrisToolbelt.removeWorld(world)) {
|
||||||
|
sender().sendMessage(C.GREEN + "Successfully removed " + world.getName() + " from bukkit.yml");
|
||||||
|
} else {
|
||||||
|
sender().sendMessage(C.YELLOW + "Looks like the world was already removed from bukkit.yml");
|
||||||
|
}
|
||||||
|
} catch (IOException e) {
|
||||||
|
sender().sendMessage(C.RED + "Failed to save bukkit.yml because of " + e.getMessage());
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
IrisToolbelt.evacuate(world, "Deleting world");
|
||||||
|
Bukkit.unloadWorld(world, false);
|
||||||
|
if (delete && world.getWorldFolder().delete()) {
|
||||||
|
sender().sendMessage(C.GREEN + "Successfully removed world folder");
|
||||||
|
} else {
|
||||||
|
sender().sendMessage(C.RED + "Failed to remove world folder");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Decree(description = "Print version information")
|
@Decree(description = "Print version information")
|
||||||
public void version() {
|
public void version() {
|
||||||
sender().sendMessage(C.GREEN + "Iris v" + Iris.instance.getDescription().getVersion() + " by Volmit Software");
|
sender().sendMessage(C.GREEN + "Iris v" + Iris.instance.getDescription().getVersion() + " by Volmit Software");
|
||||||
@@ -107,13 +138,19 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
sender().sendMessage(C.GREEN + "Total Height: " + (sender().player().getWorld().getMaxHeight() - sender().player().getWorld().getMinHeight()));
|
sender().sendMessage(C.GREEN + "Total Height: " + (sender().player().getWorld().getMaxHeight() - sender().player().getWorld().getMinHeight()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Decree(description = "QOL command to open a overworld studio world.", sync = true)
|
||||||
|
public void so() {
|
||||||
|
sender().sendMessage(C.GREEN + "Opening studio for the \"Overworld\" pack (seed: 1337)");
|
||||||
|
Iris.service(StudioSVC.class).open(sender(), 1337, "overworld");
|
||||||
|
}
|
||||||
|
|
||||||
@Decree(description = "Set aura spins")
|
@Decree(description = "Set aura spins")
|
||||||
public void aura(
|
public void aura(
|
||||||
@Param(description = "The h color value", defaultValue = "-20")
|
@Param(description = "The h color value", defaultValue = "-20")
|
||||||
int h,
|
int h,
|
||||||
@Param(description = "The s color value", defaultValue = "7")
|
@Param(description = "The s color value", defaultValue = "7")
|
||||||
int s,
|
int s,
|
||||||
@Param(description = "The b color value", defaultValue = "8")
|
@Param(description = "The b color value", defaultValue = "8")
|
||||||
int b
|
int b
|
||||||
) {
|
) {
|
||||||
IrisSettings.get().getGeneral().setSpinh(h);
|
IrisSettings.get().getGeneral().setSpinh(h);
|
||||||
@@ -125,15 +162,15 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Bitwise calculations")
|
@Decree(description = "Bitwise calculations")
|
||||||
public void bitwise(
|
public void bitwise(
|
||||||
@Param(description = "The first value to run calculations on")
|
@Param(description = "The first value to run calculations on")
|
||||||
int value1,
|
int value1,
|
||||||
@Param(description = "The operator: | & ^ ≺≺ ≻≻ %")
|
@Param(description = "The operator: | & ^ ≺≺ ≻≻ %")
|
||||||
String operator,
|
String operator,
|
||||||
@Param(description = "The second value to run calculations on")
|
@Param(description = "The second value to run calculations on")
|
||||||
int value2
|
int value2
|
||||||
) {
|
) {
|
||||||
Integer v = null;
|
Integer v = null;
|
||||||
switch(operator) {
|
switch (operator) {
|
||||||
case "|" -> v = value1 | value2;
|
case "|" -> v = value1 | value2;
|
||||||
case "&" -> v = value1 & value2;
|
case "&" -> v = value1 & value2;
|
||||||
case "^" -> v = value1 ^ value2;
|
case "^" -> v = value1 ^ value2;
|
||||||
@@ -141,7 +178,7 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
case ">>" -> v = value1 >> value2;
|
case ">>" -> v = value1 >> value2;
|
||||||
case "<<" -> v = value1 << value2;
|
case "<<" -> v = value1 << value2;
|
||||||
}
|
}
|
||||||
if(v == null) {
|
if (v == null) {
|
||||||
sender().sendMessage(C.RED + "The operator you entered: (" + operator + ") is invalid!");
|
sender().sendMessage(C.RED + "The operator you entered: (" + operator + ") is invalid!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -150,7 +187,7 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Toggle debug")
|
@Decree(description = "Toggle debug")
|
||||||
public void debug(
|
public void debug(
|
||||||
@Param(name = "on", description = "Whether or not debug should be on", defaultValue = "other")
|
@Param(name = "on", description = "Whether or not debug should be on", defaultValue = "other")
|
||||||
Boolean on
|
Boolean on
|
||||||
) {
|
) {
|
||||||
boolean to = on == null ? !IrisSettings.get().getGeneral().isDebug() : on;
|
boolean to = on == null ? !IrisSettings.get().getGeneral().isDebug() : on;
|
||||||
@@ -161,23 +198,27 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Download a project.", aliases = "dl")
|
@Decree(description = "Download a project.", aliases = "dl")
|
||||||
public void download(
|
public void download(
|
||||||
@Param(name = "pack", description = "The pack to download", defaultValue = "overworld", aliases = "project")
|
@Param(name = "pack", description = "The pack to download", defaultValue = "overworld", aliases = "project")
|
||||||
String pack,
|
String pack,
|
||||||
@Param(name = "branch", description = "The branch to download from", defaultValue = "main")
|
@Param(name = "branch", description = "The branch to download from", defaultValue = "main")
|
||||||
String branch,
|
String branch,
|
||||||
@Param(name = "trim", description = "Whether or not to download a trimmed version (do not enable when editing)", defaultValue = "false")
|
@Param(name = "trim", description = "Whether or not to download a trimmed version (do not enable when editing)", defaultValue = "false")
|
||||||
boolean trim,
|
boolean trim,
|
||||||
@Param(name = "overwrite", description = "Whether or not to overwrite the pack with the downloaded one", aliases = "force", defaultValue = "false")
|
@Param(name = "overwrite", description = "Whether or not to overwrite the pack with the downloaded one", aliases = "force", defaultValue = "false")
|
||||||
boolean overwrite
|
boolean overwrite
|
||||||
) {
|
) {
|
||||||
branch = pack.equals("overworld") ? "stable" : branch;
|
|
||||||
sender().sendMessage(C.GREEN + "Downloading pack: " + pack + "/" + branch + (trim ? " trimmed" : "") + (overwrite ? " overwriting" : ""));
|
sender().sendMessage(C.GREEN + "Downloading pack: " + pack + "/" + branch + (trim ? " trimmed" : "") + (overwrite ? " overwriting" : ""));
|
||||||
Iris.service(StudioSVC.class).downloadSearch(sender(), "IrisDimensions/" + pack + "/" + branch, trim, overwrite);
|
if (pack.equals("overworld")) {
|
||||||
|
String url = "https://github.com/IrisDimensions/overworld/releases/download/" + Iris.OVERWORLD_TAG + "/overworld.zip";
|
||||||
|
Iris.service(StudioSVC.class).downloadRelease(sender(), url, trim, overwrite);
|
||||||
|
} else {
|
||||||
|
Iris.service(StudioSVC.class).downloadSearch(sender(), "IrisDimensions/" + pack + "/" + branch, trim, overwrite);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Decree(description = "Get metrics for your world", aliases = "measure", origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Get metrics for your world", aliases = "measure", origin = DecreeOrigin.PLAYER)
|
||||||
public void metrics() {
|
public void metrics() {
|
||||||
if(!IrisToolbelt.isIrisWorld(world())) {
|
if (!IrisToolbelt.isIrisWorld(world())) {
|
||||||
sender().sendMessage(C.RED + "You must be in an Iris world");
|
sender().sendMessage(C.RED + "You must be in an Iris world");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -194,10 +235,10 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(name = "regen", description = "Regenerate nearby chunks.", aliases = "rg", sync = true, origin = DecreeOrigin.PLAYER)
|
@Decree(name = "regen", description = "Regenerate nearby chunks.", aliases = "rg", sync = true, origin = DecreeOrigin.PLAYER)
|
||||||
public void regen(
|
public void regen(
|
||||||
@Param(name = "radius", description = "The radius of nearby cunks", defaultValue = "5")
|
@Param(name = "radius", description = "The radius of nearby cunks", defaultValue = "5")
|
||||||
int radius
|
int radius
|
||||||
) {
|
) {
|
||||||
if(IrisToolbelt.isIrisWorld(player().getWorld())) {
|
if (IrisToolbelt.isIrisWorld(player().getWorld())) {
|
||||||
VolmitSender sender = sender();
|
VolmitSender sender = sender();
|
||||||
J.a(() -> {
|
J.a(() -> {
|
||||||
DecreeContext.touch(sender);
|
DecreeContext.touch(sender);
|
||||||
@@ -209,18 +250,18 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
BurstExecutor b = MultiBurst.burst.burst();
|
BurstExecutor b = MultiBurst.burst.burst();
|
||||||
b.setMulticore(false);
|
b.setMulticore(false);
|
||||||
int rad = engine.getMantle().getRealRadius();
|
int rad = engine.getMantle().getRealRadius();
|
||||||
for(int i = -(radius + rad); i <= radius + rad; i++) {
|
for (int i = -(radius + rad); i <= radius + rad; i++) {
|
||||||
for(int j = -(radius + rad); j <= radius + rad; j++) {
|
for (int j = -(radius + rad); j <= radius + rad; j++) {
|
||||||
engine.getMantle().getMantle().deleteChunk(i + cx.getX(), j + cx.getZ());
|
engine.getMantle().getMantle().deleteChunk(i + cx.getX(), j + cx.getZ());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for(int i = -radius; i <= radius; i++) {
|
for (int i = -radius; i <= radius; i++) {
|
||||||
for(int j = -radius; j <= radius; j++) {
|
for (int j = -radius; j <= radius; j++) {
|
||||||
int finalJ = j;
|
int finalJ = j;
|
||||||
int finalI = i;
|
int finalI = i;
|
||||||
b.queue(() -> plat.injectChunkReplacement(player().getWorld(), finalI + cx.getX(), finalJ + cx.getZ(), (f) -> {
|
b.queue(() -> plat.injectChunkReplacement(player().getWorld(), finalI + cx.getX(), finalJ + cx.getZ(), (f) -> {
|
||||||
synchronized(js) {
|
synchronized (js) {
|
||||||
js.add(f);
|
js.add(f);
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
@@ -236,11 +277,11 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
public void execute(Runnable runnable) {
|
public void execute(Runnable runnable) {
|
||||||
futures.add(J.sfut(runnable));
|
futures.add(J.sfut(runnable));
|
||||||
|
|
||||||
if(futures.size() > 64) {
|
if (futures.size() > 64) {
|
||||||
while(futures.isNotEmpty()) {
|
while (futures.isNotEmpty()) {
|
||||||
try {
|
try {
|
||||||
futures.remove(0).get();
|
futures.remove(0).get();
|
||||||
} catch(InterruptedException | ExecutionException e) {
|
} catch (InterruptedException | ExecutionException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -254,7 +295,7 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
};
|
};
|
||||||
r.queue(js);
|
r.queue(js);
|
||||||
r.execute(sender());
|
r.execute(sender());
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
sender().sendMessage("Unable to parse view-distance");
|
sender().sendMessage("Unable to parse view-distance");
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -265,26 +306,26 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Update the pack of a world (UNSAFE!)", name = "^world", aliases = "update-world")
|
@Decree(description = "Update the pack of a world (UNSAFE!)", name = "^world", aliases = "update-world")
|
||||||
public void updateWorld(
|
public void updateWorld(
|
||||||
@Param(description = "The world to update", contextual = true)
|
@Param(description = "The world to update", contextual = true)
|
||||||
World world,
|
World world,
|
||||||
@Param(description = "The pack to install into the world", contextual = true, aliases = "dimension")
|
@Param(description = "The pack to install into the world", contextual = true, aliases = "dimension")
|
||||||
IrisDimension pack,
|
IrisDimension pack,
|
||||||
@Param(description = "Make sure to make a backup & read the warnings first!", defaultValue = "false", aliases = "c")
|
@Param(description = "Make sure to make a backup & read the warnings first!", defaultValue = "false", aliases = "c")
|
||||||
boolean confirm,
|
boolean confirm,
|
||||||
@Param(description = "Should Iris download the pack again for you", defaultValue = "false", name = "fresh-download", aliases = {"fresh", "new"})
|
@Param(description = "Should Iris download the pack again for you", defaultValue = "false", name = "fresh-download", aliases = {"fresh", "new"})
|
||||||
boolean freshDownload
|
boolean freshDownload
|
||||||
) {
|
) {
|
||||||
if(!confirm) {
|
if (!confirm) {
|
||||||
sender().sendMessage(new String[] {
|
sender().sendMessage(new String[]{
|
||||||
C.RED + "You should always make a backup before using this",
|
C.RED + "You should always make a backup before using this",
|
||||||
C.YELLOW + "Issues caused by this can be, but are not limited to:",
|
C.YELLOW + "Issues caused by this can be, but are not limited to:",
|
||||||
C.YELLOW + " - Broken chunks (cut-offs) between old and new chunks (before & after the update)",
|
C.YELLOW + " - Broken chunks (cut-offs) between old and new chunks (before & after the update)",
|
||||||
C.YELLOW + " - Regenerated chunks that do not fit in with the old chunks",
|
C.YELLOW + " - Regenerated chunks that do not fit in with the old chunks",
|
||||||
C.YELLOW + " - Structures not spawning again when regenerating",
|
C.YELLOW + " - Structures not spawning again when regenerating",
|
||||||
C.YELLOW + " - Caves not lining up",
|
C.YELLOW + " - Caves not lining up",
|
||||||
C.YELLOW + " - Terrain layers not lining up",
|
C.YELLOW + " - Terrain layers not lining up",
|
||||||
C.RED + "Now that you are aware of the risks, and have made a back-up:",
|
C.RED + "Now that you are aware of the risks, and have made a back-up:",
|
||||||
C.RED + "/iris ^world <world> <pack> confirm=true"
|
C.RED + "/iris ^world " + world.getName() + " " + pack.getLoadKey() + " confirm=true"
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -292,7 +333,7 @@ public class CommandIris implements DecreeExecutor {
|
|||||||
File folder = world.getWorldFolder();
|
File folder = world.getWorldFolder();
|
||||||
folder.mkdirs();
|
folder.mkdirs();
|
||||||
|
|
||||||
if(freshDownload) {
|
if (freshDownload) {
|
||||||
Iris.service(StudioSVC.class).downloadSearch(sender(), pack.getLoadKey(), false, true);
|
Iris.service(StudioSVC.class).downloadSearch(sender(), pack.getLoadKey(), false, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -42,7 +42,7 @@ import java.io.File;
|
|||||||
public class CommandJigsaw implements DecreeExecutor {
|
public class CommandJigsaw implements DecreeExecutor {
|
||||||
@Decree(description = "Edit a jigsaw piece")
|
@Decree(description = "Edit a jigsaw piece")
|
||||||
public void edit(
|
public void edit(
|
||||||
@Param(description = "The jigsaw piece to edit")
|
@Param(description = "The jigsaw piece to edit")
|
||||||
IrisJigsawPiece piece
|
IrisJigsawPiece piece
|
||||||
) {
|
) {
|
||||||
File dest = piece.getLoadFile();
|
File dest = piece.getLoadFile();
|
||||||
@@ -51,7 +51,7 @@ public class CommandJigsaw implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Place a jigsaw structure")
|
@Decree(description = "Place a jigsaw structure")
|
||||||
public void place(
|
public void place(
|
||||||
@Param(description = "The jigsaw structure to place")
|
@Param(description = "The jigsaw structure to place")
|
||||||
IrisJigsawStructure structure
|
IrisJigsawStructure structure
|
||||||
) {
|
) {
|
||||||
PrecisionStopwatch p = PrecisionStopwatch.start();
|
PrecisionStopwatch p = PrecisionStopwatch.start();
|
||||||
@@ -62,16 +62,16 @@ public class CommandJigsaw implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Create a jigsaw piece")
|
@Decree(description = "Create a jigsaw piece")
|
||||||
public void create(
|
public void create(
|
||||||
@Param(description = "The name of the jigsaw piece")
|
@Param(description = "The name of the jigsaw piece")
|
||||||
String piece,
|
String piece,
|
||||||
@Param(description = "The project to add the jigsaw piece to")
|
@Param(description = "The project to add the jigsaw piece to")
|
||||||
String project,
|
String project,
|
||||||
@Param(description = "The object to use for this piece", customHandler = ObjectHandler.class)
|
@Param(description = "The object to use for this piece", customHandler = ObjectHandler.class)
|
||||||
String object
|
String object
|
||||||
) {
|
) {
|
||||||
IrisObject o = IrisData.loadAnyObject(object);
|
IrisObject o = IrisData.loadAnyObject(object);
|
||||||
|
|
||||||
if(object == null) {
|
if (object == null) {
|
||||||
sender().sendMessage(C.RED + "Failed to find existing object");
|
sender().sendMessage(C.RED + "Failed to find existing object");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -88,7 +88,7 @@ public class CommandJigsaw implements DecreeExecutor {
|
|||||||
public void exit() {
|
public void exit() {
|
||||||
JigsawEditor editor = JigsawEditor.editors.get(player());
|
JigsawEditor editor = JigsawEditor.editors.get(player());
|
||||||
|
|
||||||
if(editor == null) {
|
if (editor == null) {
|
||||||
sender().sendMessage(C.GOLD + "You don't have any pieces open to exit!");
|
sender().sendMessage(C.GOLD + "You don't have any pieces open to exit!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -101,7 +101,7 @@ public class CommandJigsaw implements DecreeExecutor {
|
|||||||
public void save() {
|
public void save() {
|
||||||
JigsawEditor editor = JigsawEditor.editors.get(player());
|
JigsawEditor editor = JigsawEditor.editors.get(player());
|
||||||
|
|
||||||
if(editor == null) {
|
if (editor == null) {
|
||||||
sender().sendMessage(C.GOLD + "You don't have any pieces open to save!");
|
sender().sendMessage(C.GOLD + "You don't have any pieces open to save!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -25,13 +25,7 @@ import com.volmit.iris.core.service.ObjectSVC;
|
|||||||
import com.volmit.iris.core.service.StudioSVC;
|
import com.volmit.iris.core.service.StudioSVC;
|
||||||
import com.volmit.iris.core.service.WandSVC;
|
import com.volmit.iris.core.service.WandSVC;
|
||||||
import com.volmit.iris.engine.framework.Engine;
|
import com.volmit.iris.engine.framework.Engine;
|
||||||
import com.volmit.iris.engine.object.IObjectPlacer;
|
import com.volmit.iris.engine.object.*;
|
||||||
import com.volmit.iris.engine.object.IrisDimension;
|
|
||||||
import com.volmit.iris.engine.object.IrisObject;
|
|
||||||
import com.volmit.iris.engine.object.IrisObjectPlacement;
|
|
||||||
import com.volmit.iris.engine.object.IrisObjectPlacementScaleInterpolator;
|
|
||||||
import com.volmit.iris.engine.object.IrisObjectRotation;
|
|
||||||
import com.volmit.iris.engine.object.TileData;
|
|
||||||
import com.volmit.iris.util.data.Cuboid;
|
import com.volmit.iris.util.data.Cuboid;
|
||||||
import com.volmit.iris.util.decree.DecreeExecutor;
|
import com.volmit.iris.util.decree.DecreeExecutor;
|
||||||
import com.volmit.iris.util.decree.DecreeOrigin;
|
import com.volmit.iris.util.decree.DecreeOrigin;
|
||||||
@@ -53,21 +47,13 @@ import org.bukkit.util.Vector;
|
|||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.text.NumberFormat;
|
import java.text.NumberFormat;
|
||||||
import java.util.ArrayList;
|
import java.util.*;
|
||||||
import java.util.Comparator;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.HashSet;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Set;
|
|
||||||
import java.util.TreeSet;
|
|
||||||
import java.util.stream.Collectors;
|
|
||||||
|
|
||||||
@Decree(name = "object", aliases = "o", origin = DecreeOrigin.PLAYER, studio = true, description = "Iris object manipulation")
|
@Decree(name = "object", aliases = "o", origin = DecreeOrigin.PLAYER, studio = true, description = "Iris object manipulation")
|
||||||
public class CommandObject implements DecreeExecutor {
|
public class CommandObject implements DecreeExecutor {
|
||||||
|
|
||||||
private static final Set<Material> skipBlocks = Set.of(Material.GRASS, Material.SNOW, Material.VINE, Material.TORCH, Material.DEAD_BUSH,
|
private static final Set<Material> skipBlocks = Set.of(Material.GRASS, Material.SNOW, Material.VINE, Material.TORCH, Material.DEAD_BUSH,
|
||||||
Material.POPPY, Material.DANDELION);
|
Material.POPPY, Material.DANDELION);
|
||||||
|
|
||||||
public static IObjectPlacer createPlacer(World world, Map<Block, BlockData> futureBlockChanges) {
|
public static IObjectPlacer createPlacer(World world, Map<Block, BlockData> futureBlockChanges) {
|
||||||
|
|
||||||
@@ -87,7 +73,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
Block block = world.getBlockAt(x, y, z);
|
Block block = world.getBlockAt(x, y, z);
|
||||||
|
|
||||||
//Prevent blocks being set in or bellow bedrock
|
//Prevent blocks being set in or bellow bedrock
|
||||||
if(y <= world.getMinHeight() || block.getType() == Material.BEDROCK) return;
|
if (y <= world.getMinHeight() || block.getType() == Material.BEDROCK) return;
|
||||||
|
|
||||||
futureBlockChanges.put(block, block.getBlockData());
|
futureBlockChanges.put(block, block.getBlockData());
|
||||||
|
|
||||||
@@ -145,7 +131,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Check the composition of an object")
|
@Decree(description = "Check the composition of an object")
|
||||||
public void analyze(
|
public void analyze(
|
||||||
@Param(description = "The object to analyze", customHandler = ObjectHandler.class)
|
@Param(description = "The object to analyze", customHandler = ObjectHandler.class)
|
||||||
String object
|
String object
|
||||||
) {
|
) {
|
||||||
IrisObject o = IrisData.loadAnyObject(object);
|
IrisObject o = IrisData.loadAnyObject(object);
|
||||||
@@ -156,19 +142,19 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
Map<Material, Set<BlockData>> unsorted = new HashMap<>();
|
Map<Material, Set<BlockData>> unsorted = new HashMap<>();
|
||||||
Map<BlockData, Integer> amounts = new HashMap<>();
|
Map<BlockData, Integer> amounts = new HashMap<>();
|
||||||
Map<Material, Integer> materials = new HashMap<>();
|
Map<Material, Integer> materials = new HashMap<>();
|
||||||
while(queue.hasNext()) {
|
while (queue.hasNext()) {
|
||||||
BlockData block = queue.next();
|
BlockData block = queue.next();
|
||||||
|
|
||||||
//unsorted.put(block.getMaterial(), block);
|
//unsorted.put(block.getMaterial(), block);
|
||||||
|
|
||||||
if(!amounts.containsKey(block)) {
|
if (!amounts.containsKey(block)) {
|
||||||
amounts.put(block, 1);
|
amounts.put(block, 1);
|
||||||
|
|
||||||
|
|
||||||
} else
|
} else
|
||||||
amounts.put(block, amounts.get(block) + 1);
|
amounts.put(block, amounts.get(block) + 1);
|
||||||
|
|
||||||
if(!materials.containsKey(block.getMaterial())) {
|
if (!materials.containsKey(block.getMaterial())) {
|
||||||
materials.put(block.getMaterial(), 1);
|
materials.put(block.getMaterial(), 1);
|
||||||
unsorted.put(block.getMaterial(), new HashSet<>());
|
unsorted.put(block.getMaterial(), new HashSet<>());
|
||||||
unsorted.get(block.getMaterial()).add(block);
|
unsorted.get(block.getMaterial()).add(block);
|
||||||
@@ -180,13 +166,13 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
List<Material> sortedMatsList = amounts.keySet().stream().map(BlockData::getMaterial)
|
List<Material> sortedMatsList = amounts.keySet().stream().map(BlockData::getMaterial)
|
||||||
.sorted().collect(Collectors.toList());
|
.sorted().toList();
|
||||||
Set<Material> sortedMats = new TreeSet<>(Comparator.comparingInt(materials::get).reversed());
|
Set<Material> sortedMats = new TreeSet<>(Comparator.comparingInt(materials::get).reversed());
|
||||||
sortedMats.addAll(sortedMatsList);
|
sortedMats.addAll(sortedMatsList);
|
||||||
sender().sendMessage("== Blocks in object ==");
|
sender().sendMessage("== Blocks in object ==");
|
||||||
|
|
||||||
int n = 0;
|
int n = 0;
|
||||||
for(Material mat : sortedMats) {
|
for (Material mat : sortedMats) {
|
||||||
int amount = materials.get(mat);
|
int amount = materials.get(mat);
|
||||||
List<BlockData> set = new ArrayList<>(unsorted.get(mat));
|
List<BlockData> set = new ArrayList<>(unsorted.get(mat));
|
||||||
set.sort(Comparator.comparingInt(amounts::get).reversed());
|
set.sort(Comparator.comparingInt(amounts::get).reversed());
|
||||||
@@ -194,17 +180,17 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
int dataAmount = amounts.get(data);
|
int dataAmount = amounts.get(data);
|
||||||
|
|
||||||
String string = " - " + mat.toString() + "*" + amount;
|
String string = " - " + mat.toString() + "*" + amount;
|
||||||
if(data.getAsString(true).contains("[")) {
|
if (data.getAsString(true).contains("[")) {
|
||||||
string = string + " --> [" + data.getAsString(true).split("\\[")[1]
|
string = string + " --> [" + data.getAsString(true).split("\\[")[1]
|
||||||
.replaceAll("true", ChatColor.GREEN + "true" + ChatColor.GRAY)
|
.replaceAll("true", ChatColor.GREEN + "true" + ChatColor.GRAY)
|
||||||
.replaceAll("false", ChatColor.RED + "false" + ChatColor.GRAY) + "*" + dataAmount;
|
.replaceAll("false", ChatColor.RED + "false" + ChatColor.GRAY) + "*" + dataAmount;
|
||||||
}
|
}
|
||||||
|
|
||||||
sender().sendMessage(string);
|
sender().sendMessage(string);
|
||||||
|
|
||||||
n++;
|
n++;
|
||||||
|
|
||||||
if(n >= 10) {
|
if (n >= 10) {
|
||||||
sender().sendMessage(" + " + (sortedMats.size() - n) + " other block types");
|
sender().sendMessage(" + " + (sortedMats.size() - n) + " other block types");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -219,16 +205,19 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Contract a selection based on your looking direction", aliases = "-")
|
@Decree(description = "Contract a selection based on your looking direction", aliases = "-")
|
||||||
public void contract(
|
public void contract(
|
||||||
@Param(description = "The amount to inset by", defaultValue = "1")
|
@Param(description = "The amount to inset by", defaultValue = "1")
|
||||||
int amount
|
int amount
|
||||||
) {
|
) {
|
||||||
if(!WandSVC.isHoldingWand(player())) {
|
if (!WandSVC.isHoldingWand(player())) {
|
||||||
sender().sendMessage("Hold your wand.");
|
sender().sendMessage("Hold your wand.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Location[] b = WandSVC.getCuboid(player());
|
Location[] b = WandSVC.getCuboid(player());
|
||||||
|
if (b == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
Location a1 = b[0].clone();
|
Location a1 = b[0].clone();
|
||||||
Location a2 = b[1].clone();
|
Location a2 = b[1].clone();
|
||||||
Cuboid cursor = new Cuboid(a1, a2);
|
Cuboid cursor = new Cuboid(a1, a2);
|
||||||
@@ -244,18 +233,21 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Set point 1 to look", aliases = "p1")
|
@Decree(description = "Set point 1 to look", aliases = "p1")
|
||||||
public void position1(
|
public void position1(
|
||||||
@Param(description = "Whether to use your current position, or where you look", defaultValue = "true")
|
@Param(description = "Whether to use your current position, or where you look", defaultValue = "true")
|
||||||
boolean here
|
boolean here
|
||||||
) {
|
) {
|
||||||
if(!WandSVC.isHoldingWand(player())) {
|
if (!WandSVC.isHoldingWand(player())) {
|
||||||
sender().sendMessage("Ready your Wand.");
|
sender().sendMessage("Ready your Wand.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(WandSVC.isHoldingWand(player())) {
|
if (WandSVC.isHoldingWand(player())) {
|
||||||
Location[] g = WandSVC.getCuboid(player());
|
Location[] g = WandSVC.getCuboid(player());
|
||||||
|
|
||||||
if(!here) {
|
if (g == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!here) {
|
||||||
// TODO: WARNING HEIGHT
|
// TODO: WARNING HEIGHT
|
||||||
g[1] = player().getTargetBlock(null, 256).getLocation().clone();
|
g[1] = player().getTargetBlock(null, 256).getLocation().clone();
|
||||||
} else {
|
} else {
|
||||||
@@ -267,18 +259,22 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Set point 2 to look", aliases = "p2")
|
@Decree(description = "Set point 2 to look", aliases = "p2")
|
||||||
public void position2(
|
public void position2(
|
||||||
@Param(description = "Whether to use your current position, or where you look", defaultValue = "true")
|
@Param(description = "Whether to use your current position, or where you look", defaultValue = "true")
|
||||||
boolean here
|
boolean here
|
||||||
) {
|
) {
|
||||||
if(!WandSVC.isHoldingWand(player())) {
|
if (!WandSVC.isHoldingWand(player())) {
|
||||||
sender().sendMessage("Ready your Wand.");
|
sender().sendMessage("Ready your Wand.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(WandSVC.isHoldingIrisWand(player())) {
|
if (WandSVC.isHoldingIrisWand(player())) {
|
||||||
Location[] g = WandSVC.getCuboid(player());
|
Location[] g = WandSVC.getCuboid(player());
|
||||||
|
|
||||||
if(!here) {
|
if (g == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!here) {
|
||||||
// TODO: WARNING HEIGHT
|
// TODO: WARNING HEIGHT
|
||||||
g[0] = player().getTargetBlock(null, 256).getLocation().clone();
|
g[0] = player().getTargetBlock(null, 256).getLocation().clone();
|
||||||
} else {
|
} else {
|
||||||
@@ -290,13 +286,13 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Paste an object", sync = true)
|
@Decree(description = "Paste an object", sync = true)
|
||||||
public void paste(
|
public void paste(
|
||||||
@Param(description = "The object to paste", customHandler = ObjectHandler.class)
|
@Param(description = "The object to paste", customHandler = ObjectHandler.class)
|
||||||
String object,
|
String object,
|
||||||
@Param(description = "Whether or not to edit the object (need to hold wand)", defaultValue = "false")
|
@Param(description = "Whether or not to edit the object (need to hold wand)", defaultValue = "false")
|
||||||
boolean edit,
|
boolean edit,
|
||||||
@Param(description = "The amount of degrees to rotate by", defaultValue = "0")
|
@Param(description = "The amount of degrees to rotate by", defaultValue = "0")
|
||||||
int rotate,
|
int rotate,
|
||||||
@Param(description = "The factor by which to scale the object placement", defaultValue = "1")
|
@Param(description = "The factor by which to scale the object placement", defaultValue = "1")
|
||||||
double scale
|
double scale
|
||||||
// ,
|
// ,
|
||||||
// @Param(description = "The scale interpolator to use", defaultValue = "none")
|
// @Param(description = "The scale interpolator to use", defaultValue = "none")
|
||||||
@@ -304,7 +300,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
) {
|
) {
|
||||||
IrisObject o = IrisData.loadAnyObject(object);
|
IrisObject o = IrisData.loadAnyObject(object);
|
||||||
double maxScale = Double.max(10 - o.getBlocks().size() / 10000d, 1);
|
double maxScale = Double.max(10 - o.getBlocks().size() / 10000d, 1);
|
||||||
if(scale > maxScale) {
|
if (scale > maxScale) {
|
||||||
sender().sendMessage(C.YELLOW + "Indicated scale exceeds maximum. Downscaled to maximum: " + maxScale);
|
sender().sendMessage(C.YELLOW + "Indicated scale exceeds maximum. Downscaled to maximum: " + maxScale);
|
||||||
scale = maxScale;
|
scale = maxScale;
|
||||||
}
|
}
|
||||||
@@ -319,8 +315,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
Map<Block, BlockData> futureChanges = new HashMap<>();
|
Map<Block, BlockData> futureChanges = new HashMap<>();
|
||||||
|
|
||||||
if(scale != 1)
|
if (scale != 1) {
|
||||||
{
|
|
||||||
o = o.scaled(scale, IrisObjectPlacementScaleInterpolator.TRICUBIC);
|
o = o.scaled(scale, IrisObjectPlacementScaleInterpolator.TRICUBIC);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -328,16 +323,16 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
Iris.service(ObjectSVC.class).addChanges(futureChanges);
|
Iris.service(ObjectSVC.class).addChanges(futureChanges);
|
||||||
|
|
||||||
if(edit) {
|
if (edit) {
|
||||||
ItemStack newWand = WandSVC.createWand(block.clone().subtract(o.getCenter()).add(o.getW() - 1,
|
ItemStack newWand = WandSVC.createWand(block.clone().subtract(o.getCenter()).add(o.getW() - 1,
|
||||||
o.getH() + o.getCenter().clone().getY() - 1, o.getD() - 1), block.clone().subtract(o.getCenter().clone().setY(0)));
|
o.getH() + o.getCenter().clone().getY() - 1, o.getD() - 1), block.clone().subtract(o.getCenter().clone().setY(0)));
|
||||||
if(WandSVC.isWand(wand)) {
|
if (WandSVC.isWand(wand)) {
|
||||||
wand = newWand;
|
wand = newWand;
|
||||||
player().getInventory().setItemInMainHand(wand);
|
player().getInventory().setItemInMainHand(wand);
|
||||||
sender().sendMessage("Updated wand for " + "objects/" + o.getLoadKey() + ".iob ");
|
sender().sendMessage("Updated wand for " + "objects/" + o.getLoadKey() + ".iob ");
|
||||||
} else {
|
} else {
|
||||||
int slot = WandSVC.findWand(player().getInventory());
|
int slot = WandSVC.findWand(player().getInventory());
|
||||||
if(slot == -1) {
|
if (slot == -1) {
|
||||||
player().getInventory().addItem(newWand);
|
player().getInventory().addItem(newWand);
|
||||||
sender().sendMessage("Given new wand for " + "objects/" + o.getLoadKey() + ".iob ");
|
sender().sendMessage("Given new wand for " + "objects/" + o.getLoadKey() + ".iob ");
|
||||||
} else {
|
} else {
|
||||||
@@ -352,29 +347,29 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Save an object")
|
@Decree(description = "Save an object")
|
||||||
public void save(
|
public void save(
|
||||||
@Param(description = "The dimension to store the object in", contextual = true)
|
@Param(description = "The dimension to store the object in", contextual = true)
|
||||||
IrisDimension dimension,
|
IrisDimension dimension,
|
||||||
@Param(description = "The file to store it in, can use / for subfolders")
|
@Param(description = "The file to store it in, can use / for subfolders")
|
||||||
String name,
|
String name,
|
||||||
@Param(description = "Overwrite existing object files", defaultValue = "false", aliases = "force")
|
@Param(description = "Overwrite existing object files", defaultValue = "false", aliases = "force")
|
||||||
boolean overwrite
|
boolean overwrite
|
||||||
) {
|
) {
|
||||||
IrisObject o = WandSVC.createSchematic(player());
|
IrisObject o = WandSVC.createSchematic(player());
|
||||||
|
|
||||||
if(o == null) {
|
if (o == null) {
|
||||||
sender().sendMessage(C.YELLOW + "You need to hold your wand!");
|
sender().sendMessage(C.YELLOW + "You need to hold your wand!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = Iris.service(StudioSVC.class).getWorkspaceFile(dimension.getLoadKey(), "objects", name + ".iob");
|
File file = Iris.service(StudioSVC.class).getWorkspaceFile(dimension.getLoadKey(), "objects", name + ".iob");
|
||||||
|
|
||||||
if(file.exists() && !overwrite) {
|
if (file.exists() && !overwrite) {
|
||||||
sender().sendMessage(C.RED + "File already exists. Set overwrite=true to overwrite it.");
|
sender().sendMessage(C.RED + "File already exists. Set overwrite=true to overwrite it.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
o.write(file);
|
o.write(file);
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
sender().sendMessage(C.RED + "Failed to save object because of an IOException: " + e.getMessage());
|
sender().sendMessage(C.RED + "Failed to save object because of an IOException: " + e.getMessage());
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
@@ -385,10 +380,10 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Shift a selection in your looking direction", aliases = "-")
|
@Decree(description = "Shift a selection in your looking direction", aliases = "-")
|
||||||
public void shift(
|
public void shift(
|
||||||
@Param(description = "The amount to shift by", defaultValue = "1")
|
@Param(description = "The amount to shift by", defaultValue = "1")
|
||||||
int amount
|
int amount
|
||||||
) {
|
) {
|
||||||
if(!WandSVC.isHoldingWand(player())) {
|
if (!WandSVC.isHoldingWand(player())) {
|
||||||
sender().sendMessage("Hold your wand.");
|
sender().sendMessage("Hold your wand.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -397,6 +392,9 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
Location a1 = b[0].clone();
|
Location a1 = b[0].clone();
|
||||||
Location a2 = b[1].clone();
|
Location a2 = b[1].clone();
|
||||||
Direction d = Direction.closest(player().getLocation().getDirection()).reverse();
|
Direction d = Direction.closest(player().getLocation().getDirection()).reverse();
|
||||||
|
if (d == null) {
|
||||||
|
return; // HOW DID THIS HAPPEN
|
||||||
|
}
|
||||||
a1.add(d.toVector().multiply(amount));
|
a1.add(d.toVector().multiply(amount));
|
||||||
a2.add(d.toVector().multiply(amount));
|
a2.add(d.toVector().multiply(amount));
|
||||||
Cuboid cursor = new Cuboid(a1, a2);
|
Cuboid cursor = new Cuboid(a1, a2);
|
||||||
@@ -409,7 +407,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Undo a number of pastes", aliases = "-")
|
@Decree(description = "Undo a number of pastes", aliases = "-")
|
||||||
public void undo(
|
public void undo(
|
||||||
@Param(description = "The amount of pastes to undo", defaultValue = "1")
|
@Param(description = "The amount of pastes to undo", defaultValue = "1")
|
||||||
int amount
|
int amount
|
||||||
) {
|
) {
|
||||||
ObjectSVC service = Iris.service(ObjectSVC.class);
|
ObjectSVC service = Iris.service(ObjectSVC.class);
|
||||||
@@ -420,15 +418,14 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Gets an object wand and grabs the current WorldEdit selection.", aliases = "we", origin = DecreeOrigin.PLAYER, studio = true)
|
@Decree(description = "Gets an object wand and grabs the current WorldEdit selection.", aliases = "we", origin = DecreeOrigin.PLAYER, studio = true)
|
||||||
public void we() {
|
public void we() {
|
||||||
if(!Bukkit.getPluginManager().isPluginEnabled("WorldEdit")) {
|
if (!Bukkit.getPluginManager().isPluginEnabled("WorldEdit")) {
|
||||||
sender().sendMessage(C.RED + "You can't get a WorldEdit selection without WorldEdit, you know.");
|
sender().sendMessage(C.RED + "You can't get a WorldEdit selection without WorldEdit, you know.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Cuboid locs = WorldEditLink.getSelection(sender().player());
|
Cuboid locs = WorldEditLink.getSelection(sender().player());
|
||||||
|
|
||||||
if(locs == null)
|
if (locs == null) {
|
||||||
{
|
|
||||||
sender().sendMessage(C.RED + "You don't have a WorldEdit selection in this world.");
|
sender().sendMessage(C.RED + "You don't have a WorldEdit selection in this world.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -446,7 +443,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(name = "x&y", description = "Autoselect up, down & out", sync = true)
|
@Decree(name = "x&y", description = "Autoselect up, down & out", sync = true)
|
||||||
public void xay() {
|
public void xay() {
|
||||||
if(!WandSVC.isHoldingWand(player())) {
|
if (!WandSVC.isHoldingWand(player())) {
|
||||||
sender().sendMessage(C.YELLOW + "Hold your wand!");
|
sender().sendMessage(C.YELLOW + "Hold your wand!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -459,7 +456,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
Cuboid cursor = new Cuboid(a1, a2);
|
Cuboid cursor = new Cuboid(a1, a2);
|
||||||
Cuboid cursorx = new Cuboid(a1, a2);
|
Cuboid cursorx = new Cuboid(a1, a2);
|
||||||
|
|
||||||
while(!cursor.containsOnly(Material.AIR)) {
|
while (!cursor.containsOnly(Material.AIR)) {
|
||||||
a1.add(new org.bukkit.util.Vector(0, 1, 0));
|
a1.add(new org.bukkit.util.Vector(0, 1, 0));
|
||||||
a2.add(new org.bukkit.util.Vector(0, 1, 0));
|
a2.add(new org.bukkit.util.Vector(0, 1, 0));
|
||||||
cursor = new Cuboid(a1, a2);
|
cursor = new Cuboid(a1, a2);
|
||||||
@@ -468,7 +465,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
a1.add(new org.bukkit.util.Vector(0, -1, 0));
|
a1.add(new org.bukkit.util.Vector(0, -1, 0));
|
||||||
a2.add(new org.bukkit.util.Vector(0, -1, 0));
|
a2.add(new org.bukkit.util.Vector(0, -1, 0));
|
||||||
|
|
||||||
while(!cursorx.containsOnly(Material.AIR)) {
|
while (!cursorx.containsOnly(Material.AIR)) {
|
||||||
a1x.add(new org.bukkit.util.Vector(0, -1, 0));
|
a1x.add(new org.bukkit.util.Vector(0, -1, 0));
|
||||||
a2x.add(new org.bukkit.util.Vector(0, -1, 0));
|
a2x.add(new org.bukkit.util.Vector(0, -1, 0));
|
||||||
cursorx = new Cuboid(a1x, a2x);
|
cursorx = new Cuboid(a1x, a2x);
|
||||||
@@ -493,7 +490,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(name = "x+y", description = "Autoselect up & out", sync = true)
|
@Decree(name = "x+y", description = "Autoselect up & out", sync = true)
|
||||||
public void xpy() {
|
public void xpy() {
|
||||||
if(!WandSVC.isHoldingWand(player())) {
|
if (!WandSVC.isHoldingWand(player())) {
|
||||||
sender().sendMessage(C.YELLOW + "Hold your wand!");
|
sender().sendMessage(C.YELLOW + "Hold your wand!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -505,7 +502,7 @@ public class CommandObject implements DecreeExecutor {
|
|||||||
Location a2 = b[1].clone();
|
Location a2 = b[1].clone();
|
||||||
Cuboid cursor = new Cuboid(a1, a2);
|
Cuboid cursor = new Cuboid(a1, a2);
|
||||||
|
|
||||||
while(!cursor.containsOnly(Material.AIR)) {
|
while (!cursor.containsOnly(Material.AIR)) {
|
||||||
a1.add(new Vector(0, 1, 0));
|
a1.add(new Vector(0, 1, 0));
|
||||||
a2.add(new Vector(0, 1, 0));
|
a2.add(new Vector(0, 1, 0));
|
||||||
cursor = new Cuboid(a1, a2);
|
cursor = new Cuboid(a1, a2);
|
||||||
|
|||||||
@@ -34,30 +34,30 @@ import org.bukkit.util.Vector;
|
|||||||
public class CommandPregen implements DecreeExecutor {
|
public class CommandPregen implements DecreeExecutor {
|
||||||
@Decree(description = "Pregenerate a world")
|
@Decree(description = "Pregenerate a world")
|
||||||
public void start(
|
public void start(
|
||||||
@Param(description = "The radius of the pregen in blocks", aliases = "size")
|
@Param(description = "The radius of the pregen in blocks", aliases = "size")
|
||||||
int radius,
|
int radius,
|
||||||
@Param(description = "The world to pregen", contextual = true)
|
@Param(description = "The world to pregen", contextual = true)
|
||||||
World world,
|
World world,
|
||||||
@Param(aliases = "middle", description = "The center location of the pregen. Use \"me\" for your current location", defaultValue = "0,0")
|
@Param(aliases = "middle", description = "The center location of the pregen. Use \"me\" for your current location", defaultValue = "0,0")
|
||||||
Vector center
|
Vector center
|
||||||
) {
|
) {
|
||||||
try {
|
try {
|
||||||
if(sender().isPlayer() && access() == null) {
|
if (sender().isPlayer() && access() == null) {
|
||||||
sender().sendMessage(C.RED + "The engine access for this world is null!");
|
sender().sendMessage(C.RED + "The engine access for this world is null!");
|
||||||
sender().sendMessage(C.RED + "Please make sure the world is loaded & the engine is initialized. Generate a new chunk, for example.");
|
sender().sendMessage(C.RED + "Please make sure the world is loaded & the engine is initialized. Generate a new chunk, for example.");
|
||||||
}
|
}
|
||||||
radius = Math.max(radius, 1024);
|
radius = Math.max(radius, 1024);
|
||||||
int w = (radius >> 9 + 1) * 2;
|
int w = (radius >> 9 + 1) * 2;
|
||||||
IrisToolbelt.pregenerate(PregenTask
|
IrisToolbelt.pregenerate(PregenTask
|
||||||
.builder()
|
.builder()
|
||||||
.center(new Position2(center))
|
.center(new Position2(center.getBlockX() >> 9, center.getBlockZ() >> 9))
|
||||||
.width(w)
|
.width(w)
|
||||||
.height(w)
|
.height(w)
|
||||||
.build(), world);
|
.build(), world);
|
||||||
String msg = C.GREEN + "Pregen started in " + C.GOLD + world.getName() + C.GREEN + " of " + C.GOLD + (radius * 2) + C.GREEN + " by " + C.GOLD + (radius * 2) + C.GREEN + " blocks from " + C.GOLD + center.getX() + "," + center.getZ();
|
String msg = C.GREEN + "Pregen started in " + C.GOLD + world.getName() + C.GREEN + " of " + C.GOLD + (radius * 2) + C.GREEN + " by " + C.GOLD + (radius * 2) + C.GREEN + " blocks from " + C.GOLD + center.getX() + "," + center.getZ();
|
||||||
sender().sendMessage(msg);
|
sender().sendMessage(msg);
|
||||||
Iris.info(msg);
|
Iris.info(msg);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
sender().sendMessage(C.RED + "Epic fail. See console.");
|
sender().sendMessage(C.RED + "Epic fail. See console.");
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
@@ -66,7 +66,7 @@ public class CommandPregen implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Stop the active pregeneration task", aliases = "x")
|
@Decree(description = "Stop the active pregeneration task", aliases = "x")
|
||||||
public void stop() {
|
public void stop() {
|
||||||
if(PregeneratorJob.shutdownInstance()) {
|
if (PregeneratorJob.shutdownInstance()) {
|
||||||
sender().sendMessage(C.GREEN + "Stopped pregeneration task");
|
sender().sendMessage(C.GREEN + "Stopped pregeneration task");
|
||||||
} else {
|
} else {
|
||||||
sender().sendMessage(C.YELLOW + "No active pregeneration tasks to stop");
|
sender().sendMessage(C.YELLOW + "No active pregeneration tasks to stop");
|
||||||
@@ -75,7 +75,7 @@ public class CommandPregen implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Pause / continue the active pregeneration task", aliases = {"t", "resume", "unpause"})
|
@Decree(description = "Pause / continue the active pregeneration task", aliases = {"t", "resume", "unpause"})
|
||||||
public void pause() {
|
public void pause() {
|
||||||
if(PregeneratorJob.pauseResume()) {
|
if (PregeneratorJob.pauseResume()) {
|
||||||
sender().sendMessage(C.GREEN + "Paused/unpaused pregeneration task, now: " + (PregeneratorJob.isPaused() ? "Paused" : "Running") + ".");
|
sender().sendMessage(C.GREEN + "Paused/unpaused pregeneration task, now: " + (PregeneratorJob.isPaused() ? "Paused" : "Running") + ".");
|
||||||
} else {
|
} else {
|
||||||
sender().sendMessage(C.YELLOW + "No active pregeneration tasks to pause/unpause.");
|
sender().sendMessage(C.YELLOW + "No active pregeneration tasks to pause/unpause.");
|
||||||
|
|||||||
@@ -28,20 +28,7 @@ import com.volmit.iris.core.service.ConversionSVC;
|
|||||||
import com.volmit.iris.core.service.StudioSVC;
|
import com.volmit.iris.core.service.StudioSVC;
|
||||||
import com.volmit.iris.core.tools.IrisToolbelt;
|
import com.volmit.iris.core.tools.IrisToolbelt;
|
||||||
import com.volmit.iris.engine.framework.Engine;
|
import com.volmit.iris.engine.framework.Engine;
|
||||||
import com.volmit.iris.engine.object.InventorySlotType;
|
import com.volmit.iris.engine.object.*;
|
||||||
import com.volmit.iris.engine.object.IrisBiome;
|
|
||||||
import com.volmit.iris.engine.object.IrisBiomePaletteLayer;
|
|
||||||
import com.volmit.iris.engine.object.IrisDimension;
|
|
||||||
import com.volmit.iris.engine.object.IrisEntity;
|
|
||||||
import com.volmit.iris.engine.object.IrisGenerator;
|
|
||||||
import com.volmit.iris.engine.object.IrisInterpolator;
|
|
||||||
import com.volmit.iris.engine.object.IrisLootTable;
|
|
||||||
import com.volmit.iris.engine.object.IrisNoiseGenerator;
|
|
||||||
import com.volmit.iris.engine.object.IrisObject;
|
|
||||||
import com.volmit.iris.engine.object.IrisObjectPlacement;
|
|
||||||
import com.volmit.iris.engine.object.IrisRegion;
|
|
||||||
import com.volmit.iris.engine.object.IrisScript;
|
|
||||||
import com.volmit.iris.engine.object.NoiseStyle;
|
|
||||||
import com.volmit.iris.util.collection.KList;
|
import com.volmit.iris.util.collection.KList;
|
||||||
import com.volmit.iris.util.collection.KMap;
|
import com.volmit.iris.util.collection.KMap;
|
||||||
import com.volmit.iris.util.collection.KSet;
|
import com.volmit.iris.util.collection.KSet;
|
||||||
@@ -61,28 +48,15 @@ import com.volmit.iris.util.math.M;
|
|||||||
import com.volmit.iris.util.math.RNG;
|
import com.volmit.iris.util.math.RNG;
|
||||||
import com.volmit.iris.util.math.Spiraler;
|
import com.volmit.iris.util.math.Spiraler;
|
||||||
import com.volmit.iris.util.noise.CNG;
|
import com.volmit.iris.util.noise.CNG;
|
||||||
import com.volmit.iris.util.parallel.MultiBurst;
|
|
||||||
import com.volmit.iris.util.scheduling.J;
|
|
||||||
import com.volmit.iris.util.scheduling.O;
|
import com.volmit.iris.util.scheduling.O;
|
||||||
import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
||||||
import com.volmit.iris.util.scheduling.jobs.Job;
|
|
||||||
import com.volmit.iris.util.scheduling.jobs.JobCollection;
|
|
||||||
import com.volmit.iris.util.scheduling.jobs.QueueJob;
|
|
||||||
import com.volmit.iris.util.scheduling.jobs.SingleJob;
|
|
||||||
import io.papermc.lib.PaperLib;
|
import io.papermc.lib.PaperLib;
|
||||||
|
import org.bukkit.*;
|
||||||
import org.bukkit.Bukkit;
|
|
||||||
import org.bukkit.Chunk;
|
|
||||||
import org.bukkit.FluidCollisionMode;
|
|
||||||
import org.bukkit.GameMode;
|
|
||||||
import org.bukkit.Location;
|
|
||||||
import org.bukkit.World;
|
|
||||||
import org.bukkit.event.inventory.InventoryType;
|
import org.bukkit.event.inventory.InventoryType;
|
||||||
import org.bukkit.inventory.Inventory;
|
import org.bukkit.inventory.Inventory;
|
||||||
import org.bukkit.util.BlockVector;
|
import org.bukkit.util.BlockVector;
|
||||||
import org.bukkit.util.Vector;
|
import org.bukkit.util.Vector;
|
||||||
|
|
||||||
import java.awt.*;
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileNotFoundException;
|
import java.io.FileNotFoundException;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
@@ -93,30 +67,26 @@ import java.time.Duration;
|
|||||||
import java.time.temporal.ChronoUnit;
|
import java.time.temporal.ChronoUnit;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.concurrent.ExecutionException;
|
|
||||||
import java.util.concurrent.Future;
|
|
||||||
import java.util.function.Consumer;
|
|
||||||
import java.util.function.Supplier;
|
import java.util.function.Supplier;
|
||||||
|
|
||||||
@Decree(name = "studio", aliases = {"std", "s"}, description = "Studio Commands", studio = true)
|
@Decree(name = "studio", aliases = {"std", "s"}, description = "Studio Commands", studio = true)
|
||||||
public class CommandStudio implements DecreeExecutor {
|
public class CommandStudio implements DecreeExecutor {
|
||||||
|
private CommandFind find;
|
||||||
|
private CommandEdit edit;
|
||||||
|
|
||||||
public static String hrf(Duration duration) {
|
public static String hrf(Duration duration) {
|
||||||
return duration.toString().substring(2).replaceAll("(\\d[HMS])(?!$)", "$1 ").toLowerCase();
|
return duration.toString().substring(2).replaceAll("(\\d[HMS])(?!$)", "$1 ").toLowerCase();
|
||||||
}
|
}
|
||||||
|
|
||||||
private CommandFind find;
|
|
||||||
private CommandEdit edit;
|
|
||||||
|
|
||||||
|
|
||||||
@Decree(description = "Download a project.", aliases = "dl")
|
@Decree(description = "Download a project.", aliases = "dl")
|
||||||
public void download(
|
public void download(
|
||||||
@Param(name = "pack", description = "The pack to download", defaultValue = "overworld", aliases = "project")
|
@Param(name = "pack", description = "The pack to download", defaultValue = "overworld", aliases = "project")
|
||||||
String pack,
|
String pack,
|
||||||
@Param(name = "branch", description = "The branch to download from", defaultValue = "master")
|
@Param(name = "branch", description = "The branch to download from", defaultValue = "master")
|
||||||
String branch,
|
String branch,
|
||||||
@Param(name = "trim", description = "Whether or not to download a trimmed version (do not enable when editing)", defaultValue = "false")
|
@Param(name = "trim", description = "Whether or not to download a trimmed version (do not enable when editing)", defaultValue = "false")
|
||||||
boolean trim,
|
boolean trim,
|
||||||
@Param(name = "overwrite", description = "Whether or not to overwrite the pack with the downloaded one", aliases = "force", defaultValue = "false")
|
@Param(name = "overwrite", description = "Whether or not to overwrite the pack with the downloaded one", aliases = "force", defaultValue = "false")
|
||||||
boolean overwrite
|
boolean overwrite
|
||||||
) {
|
) {
|
||||||
new CommandIris().download(pack, branch, trim, overwrite);
|
new CommandIris().download(pack, branch, trim, overwrite);
|
||||||
@@ -124,9 +94,9 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Open a new studio world", aliases = "o", sync = true)
|
@Decree(description = "Open a new studio world", aliases = "o", sync = true)
|
||||||
public void open(
|
public void open(
|
||||||
@Param(defaultValue = "default", description = "The dimension to open a studio for", aliases = "dim")
|
@Param(defaultValue = "default", description = "The dimension to open a studio for", aliases = "dim")
|
||||||
IrisDimension dimension,
|
IrisDimension dimension,
|
||||||
@Param(defaultValue = "1337", description = "The seed to generate the studio with", aliases = "s")
|
@Param(defaultValue = "1337", description = "The seed to generate the studio with", aliases = "s")
|
||||||
long seed) {
|
long seed) {
|
||||||
sender().sendMessage(C.GREEN + "Opening studio for the \"" + dimension.getName() + "\" pack (seed: " + seed + ")");
|
sender().sendMessage(C.GREEN + "Opening studio for the \"" + dimension.getName() + "\" pack (seed: " + seed + ")");
|
||||||
Iris.service(StudioSVC.class).open(sender(), seed, dimension.getLoadKey());
|
Iris.service(StudioSVC.class).open(sender(), seed, dimension.getLoadKey());
|
||||||
@@ -134,7 +104,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Open VSCode for a dimension", aliases = {"vsc", "edit"})
|
@Decree(description = "Open VSCode for a dimension", aliases = {"vsc", "edit"})
|
||||||
public void vscode(
|
public void vscode(
|
||||||
@Param(defaultValue = "default", description = "The dimension to open VSCode for", aliases = "dim")
|
@Param(defaultValue = "default", description = "The dimension to open VSCode for", aliases = "dim")
|
||||||
IrisDimension dimension
|
IrisDimension dimension
|
||||||
) {
|
) {
|
||||||
sender().sendMessage(C.GREEN + "Opening VSCode for the \"" + dimension.getName() + "\" pack");
|
sender().sendMessage(C.GREEN + "Opening VSCode for the \"" + dimension.getName() + "\" pack");
|
||||||
@@ -143,7 +113,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Close an open studio project", aliases = {"x", "c"}, sync = true)
|
@Decree(description = "Close an open studio project", aliases = {"x", "c"}, sync = true)
|
||||||
public void close() {
|
public void close() {
|
||||||
if(!Iris.service(StudioSVC.class).isProjectOpen()) {
|
if (!Iris.service(StudioSVC.class).isProjectOpen()) {
|
||||||
sender().sendMessage(C.RED + "No open studio projects.");
|
sender().sendMessage(C.RED + "No open studio projects.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -154,144 +124,20 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Create a new studio project", aliases = "+", sync = true)
|
@Decree(description = "Create a new studio project", aliases = "+", sync = true)
|
||||||
public void create(
|
public void create(
|
||||||
@Param(description = "The name of this new Iris Project.")
|
@Param(description = "The name of this new Iris Project.")
|
||||||
String name,
|
String name,
|
||||||
@Param(description = "Copy the contents of an existing project in your packs folder and use it as a template in this new project.", contextual = true)
|
@Param(description = "Copy the contents of an existing project in your packs folder and use it as a template in this new project.", contextual = true)
|
||||||
IrisDimension template) {
|
IrisDimension template) {
|
||||||
if(template != null) {
|
if (template != null) {
|
||||||
Iris.service(StudioSVC.class).create(sender(), name, template.getLoadKey());
|
Iris.service(StudioSVC.class).create(sender(), name, template.getLoadKey());
|
||||||
} else {
|
} else {
|
||||||
Iris.service(StudioSVC.class).create(sender(), name);
|
Iris.service(StudioSVC.class).create(sender(), name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Decree(description = "Clean an Iris Project, optionally beautifying JSON & fixing block ids with missing keys. Also rebuilds the vscode schemas. ")
|
|
||||||
public void clean(
|
|
||||||
@Param(description = "The project to update", contextual = true)
|
|
||||||
IrisDimension project,
|
|
||||||
|
|
||||||
@Param(defaultValue = "true", description = "Filters all valid JSON files with a beautifier (indentation: 4)")
|
|
||||||
boolean beautify,
|
|
||||||
|
|
||||||
@Param(name = "fix-ids", defaultValue = "true", description = "Fixes any block ids used such as \"dirt\" will be converted to \"minecraft:dirt\"")
|
|
||||||
boolean fixIds,
|
|
||||||
|
|
||||||
@Param(name = "rewrite-objects", defaultValue = "false", description = "Imports all objects and re-writes them cleaning up positions & block data in the process.")
|
|
||||||
boolean rewriteObjects
|
|
||||||
) {
|
|
||||||
KList<Job> jobs = new KList<>();
|
|
||||||
KList<File> files = new KList<File>();
|
|
||||||
files(Iris.instance.getDataFolder("packs", project.getLoadKey()), files);
|
|
||||||
MultiBurst burst = MultiBurst.burst;
|
|
||||||
|
|
||||||
jobs.add(new SingleJob("Updating Workspace", () -> {
|
|
||||||
if(!new IrisProject(Iris.service(StudioSVC.class).getWorkspaceFolder(project.getLoadKey())).updateWorkspace()) {
|
|
||||||
sender().sendMessage(C.GOLD + "Invalid project: " + project.getLoadKey() + ". Try deleting the code-workspace file and try again.");
|
|
||||||
}
|
|
||||||
J.sleep(250);
|
|
||||||
}));
|
|
||||||
|
|
||||||
sender().sendMessage("Files: " + files.size());
|
|
||||||
|
|
||||||
if(fixIds) {
|
|
||||||
QueueJob<File> r = new QueueJob<>() {
|
|
||||||
@Override
|
|
||||||
public void execute(File f) {
|
|
||||||
try {
|
|
||||||
JSONObject p = new JSONObject(IO.readAll(f));
|
|
||||||
fixBlocks(p);
|
|
||||||
J.sleep(1);
|
|
||||||
IO.writeAll(f, p.toString(4));
|
|
||||||
|
|
||||||
} catch(IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getName() {
|
|
||||||
return "Fixing IDs";
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
r.queue(files);
|
|
||||||
jobs.add(r);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(beautify) {
|
|
||||||
QueueJob<File> r = new QueueJob<>() {
|
|
||||||
@Override
|
|
||||||
public void execute(File f) {
|
|
||||||
try {
|
|
||||||
JSONObject p = new JSONObject(IO.readAll(f));
|
|
||||||
IO.writeAll(f, p.toString(4));
|
|
||||||
J.sleep(1);
|
|
||||||
} catch(IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getName() {
|
|
||||||
return "Beautify";
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
r.queue(files);
|
|
||||||
jobs.add(r);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(rewriteObjects) {
|
|
||||||
QueueJob<Runnable> q = new QueueJob<>() {
|
|
||||||
@Override
|
|
||||||
public void execute(Runnable runnable) {
|
|
||||||
runnable.run();
|
|
||||||
J.sleep(50);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public String getName() {
|
|
||||||
return "Rewriting Objects";
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
IrisData data = IrisData.get(Iris.service(StudioSVC.class).getWorkspaceFolder(project.getLoadKey()));
|
|
||||||
for(String f : data.getObjectLoader().getPossibleKeys()) {
|
|
||||||
Future<?> gg = burst.complete(() -> {
|
|
||||||
File ff = data.getObjectLoader().findFile(f);
|
|
||||||
IrisObject oo = new IrisObject(0, 0, 0);
|
|
||||||
try {
|
|
||||||
oo.read(ff);
|
|
||||||
} catch(Throwable e) {
|
|
||||||
Iris.error("FAILER TO READ: " + f);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
oo.write(ff);
|
|
||||||
} catch(IOException e) {
|
|
||||||
Iris.error("FAILURE TO WRITE: " + oo.getLoadFile());
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
q.queue(() -> {
|
|
||||||
try {
|
|
||||||
gg.get();
|
|
||||||
} catch(InterruptedException | ExecutionException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
jobs.add(q);
|
|
||||||
}
|
|
||||||
|
|
||||||
new JobCollection("Cleaning", jobs).execute(sender());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Decree(description = "Get the version of a pack")
|
@Decree(description = "Get the version of a pack")
|
||||||
public void version(
|
public void version(
|
||||||
@Param(defaultValue = "default", description = "The dimension get the version of", aliases = "dim", contextual = true)
|
@Param(defaultValue = "default", description = "The dimension get the version of", aliases = "dim", contextual = true)
|
||||||
IrisDimension dimension
|
IrisDimension dimension
|
||||||
) {
|
) {
|
||||||
sender().sendMessage(C.GREEN + "The \"" + dimension.getName() + "\" pack has version: " + dimension.getVersion());
|
sender().sendMessage(C.GREEN + "The \"" + dimension.getName() + "\" pack has version: " + dimension.getVersion());
|
||||||
@@ -305,7 +151,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Execute a script", aliases = "run", origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Execute a script", aliases = "run", origin = DecreeOrigin.PLAYER)
|
||||||
public void execute(
|
public void execute(
|
||||||
@Param(description = "The script to run")
|
@Param(description = "The script to run")
|
||||||
IrisScript script
|
IrisScript script
|
||||||
) {
|
) {
|
||||||
engine().getExecution().execute(script.getLoadKey());
|
engine().getExecution().execute(script.getLoadKey());
|
||||||
@@ -313,14 +159,14 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Open the noise explorer (External GUI)", aliases = {"nmap", "n"})
|
@Decree(description = "Open the noise explorer (External GUI)", aliases = {"nmap", "n"})
|
||||||
public void noise() {
|
public void noise() {
|
||||||
if(noGUI()) return;
|
if (noGUI()) return;
|
||||||
sender().sendMessage(C.GREEN + "Opening Noise Explorer!");
|
sender().sendMessage(C.GREEN + "Opening Noise Explorer!");
|
||||||
NoiseExplorerGUI.launch();
|
NoiseExplorerGUI.launch();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Decree(description = "Charges all spawners in the area", aliases = "zzt", origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Charges all spawners in the area", aliases = "zzt", origin = DecreeOrigin.PLAYER)
|
||||||
public void charge() {
|
public void charge() {
|
||||||
if(!IrisToolbelt.isIrisWorld(world())) {
|
if (!IrisToolbelt.isIrisWorld(world())) {
|
||||||
sender().sendMessage(C.RED + "You must be in an Iris world to charge spawners!");
|
sender().sendMessage(C.RED + "You must be in an Iris world to charge spawners!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -330,17 +176,17 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Preview noise gens (External GUI)", aliases = {"generator", "gen"})
|
@Decree(description = "Preview noise gens (External GUI)", aliases = {"generator", "gen"})
|
||||||
public void explore(
|
public void explore(
|
||||||
@Param(description = "The generator to explore", contextual = true)
|
@Param(description = "The generator to explore", contextual = true)
|
||||||
IrisGenerator generator,
|
IrisGenerator generator,
|
||||||
@Param(description = "The seed to generate with", defaultValue = "12345")
|
@Param(description = "The seed to generate with", defaultValue = "12345")
|
||||||
long seed
|
long seed
|
||||||
) {
|
) {
|
||||||
if(noGUI()) return;
|
if (noGUI()) return;
|
||||||
sender().sendMessage(C.GREEN + "Opening Noise Explorer!");
|
sender().sendMessage(C.GREEN + "Opening Noise Explorer!");
|
||||||
|
|
||||||
Supplier<Function2<Double, Double, Double>> l = () -> {
|
Supplier<Function2<Double, Double, Double>> l = () -> {
|
||||||
|
|
||||||
if(generator == null) {
|
if (generator == null) {
|
||||||
return (x, z) -> 0D;
|
return (x, z) -> 0D;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -351,7 +197,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Hotload a studio", aliases = {"reload", "h"})
|
@Decree(description = "Hotload a studio", aliases = {"reload", "h"})
|
||||||
public void hotload() {
|
public void hotload() {
|
||||||
if(!Iris.service(StudioSVC.class).isProjectOpen()) {
|
if (!Iris.service(StudioSVC.class).isProjectOpen()) {
|
||||||
sender().sendMessage(C.RED + "No studio world open!");
|
sender().sendMessage(C.RED + "No studio world open!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -361,19 +207,19 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Show loot if a chest were right here", origin = DecreeOrigin.PLAYER, sync = true)
|
@Decree(description = "Show loot if a chest were right here", origin = DecreeOrigin.PLAYER, sync = true)
|
||||||
public void loot(
|
public void loot(
|
||||||
@Param(description = "Fast insertion of items in virtual inventory (may cause performance drop)", defaultValue = "false")
|
@Param(description = "Fast insertion of items in virtual inventory (may cause performance drop)", defaultValue = "false")
|
||||||
boolean fast,
|
boolean fast,
|
||||||
@Param(description = "Whether or not to append to the inventory currently open (if false, clears opened inventory)", defaultValue = "true")
|
@Param(description = "Whether or not to append to the inventory currently open (if false, clears opened inventory)", defaultValue = "true")
|
||||||
boolean add
|
boolean add
|
||||||
) {
|
) {
|
||||||
if(noStudio()) return;
|
if (noStudio()) return;
|
||||||
|
|
||||||
KList<IrisLootTable> tables = engine().getLootTables(RNG.r, player().getLocation().getBlock());
|
KList<IrisLootTable> tables = engine().getLootTables(RNG.r, player().getLocation().getBlock());
|
||||||
Inventory inv = Bukkit.createInventory(null, 27 * 2);
|
Inventory inv = Bukkit.createInventory(null, 27 * 2);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
engine().addItems(true, inv, RNG.r, tables, InventorySlotType.STORAGE, player().getLocation().getBlockX(), player().getLocation().getBlockY(), player().getLocation().getBlockZ(), 1);
|
engine().addItems(true, inv, RNG.r, tables, InventorySlotType.STORAGE, player().getLocation().getBlockX(), player().getLocation().getBlockY(), player().getLocation().getBlockZ(), 1);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage(C.RED + "Cannot add items to virtual inventory because of: " + e.getMessage());
|
sender().sendMessage(C.RED + "Cannot add items to virtual inventory because of: " + e.getMessage());
|
||||||
return;
|
return;
|
||||||
@@ -385,13 +231,13 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
ta.set(Bukkit.getScheduler().scheduleSyncRepeatingTask(Iris.instance, () ->
|
ta.set(Bukkit.getScheduler().scheduleSyncRepeatingTask(Iris.instance, () ->
|
||||||
{
|
{
|
||||||
if(!player().getOpenInventory().getType().equals(InventoryType.CHEST)) {
|
if (!player().getOpenInventory().getType().equals(InventoryType.CHEST)) {
|
||||||
Bukkit.getScheduler().cancelTask(ta.get());
|
Bukkit.getScheduler().cancelTask(ta.get());
|
||||||
sender().sendMessage(C.GREEN + "Opened inventory!");
|
sender().sendMessage(C.GREEN + "Opened inventory!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!add) {
|
if (!add) {
|
||||||
inv.clear();
|
inv.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -404,12 +250,12 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Render a world map (External GUI)", aliases = "render")
|
@Decree(description = "Render a world map (External GUI)", aliases = "render")
|
||||||
public void map(
|
public void map(
|
||||||
@Param(name = "world", description = "The world to open the generator for", contextual = true)
|
@Param(name = "world", description = "The world to open the generator for", contextual = true)
|
||||||
World world
|
World world
|
||||||
) {
|
) {
|
||||||
if(noGUI()) return;
|
if (noGUI()) return;
|
||||||
|
|
||||||
if(!IrisToolbelt.isIrisWorld(world)) {
|
if (!IrisToolbelt.isIrisWorld(world)) {
|
||||||
sender().sendMessage(C.RED + "You need to be in or specify an Iris-generated world!");
|
sender().sendMessage(C.RED + "You need to be in or specify an Iris-generated world!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -420,11 +266,11 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Package a dimension into a compressed format", aliases = "package")
|
@Decree(description = "Package a dimension into a compressed format", aliases = "package")
|
||||||
public void pkg(
|
public void pkg(
|
||||||
@Param(name = "dimension", description = "The dimension pack to compress", contextual = true, defaultValue = "default")
|
@Param(name = "dimension", description = "The dimension pack to compress", contextual = true, defaultValue = "default")
|
||||||
IrisDimension dimension,
|
IrisDimension dimension,
|
||||||
@Param(name = "obfuscate", description = "Whether or not to obfuscate the pack", defaultValue = "false")
|
@Param(name = "obfuscate", description = "Whether or not to obfuscate the pack", defaultValue = "false")
|
||||||
boolean obfuscate,
|
boolean obfuscate,
|
||||||
@Param(name = "minify", description = "Whether or not to minify the pack", defaultValue = "true")
|
@Param(name = "minify", description = "Whether or not to minify the pack", defaultValue = "true")
|
||||||
boolean minify
|
boolean minify
|
||||||
) {
|
) {
|
||||||
Iris.service(StudioSVC.class).compilePackage(sender(), dimension.getLoadKey(), obfuscate, minify);
|
Iris.service(StudioSVC.class).compilePackage(sender(), dimension.getLoadKey(), obfuscate, minify);
|
||||||
@@ -432,7 +278,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Profiles the performance of a dimension", origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Profiles the performance of a dimension", origin = DecreeOrigin.PLAYER)
|
||||||
public void profile(
|
public void profile(
|
||||||
@Param(description = "The dimension to profile", contextual = true, defaultValue = "default")
|
@Param(description = "The dimension to profile", contextual = true, defaultValue = "default")
|
||||||
IrisDimension dimension
|
IrisDimension dimension
|
||||||
) {
|
) {
|
||||||
File pack = dimension.getLoadFile().getParentFile().getParentFile();
|
File pack = dimension.getLoadFile().getParentFile().getParentFile();
|
||||||
@@ -450,17 +296,17 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
sender().sendMessage("Calculating Performance Metrics for Noise generators");
|
sender().sendMessage("Calculating Performance Metrics for Noise generators");
|
||||||
|
|
||||||
for(NoiseStyle i : NoiseStyle.values()) {
|
for (NoiseStyle i : NoiseStyle.values()) {
|
||||||
CNG c = i.create(new RNG(i.hashCode()));
|
CNG c = i.create(new RNG(i.hashCode()));
|
||||||
|
|
||||||
for(int j = 0; j < 3000; j++) {
|
for (int j = 0; j < 3000; j++) {
|
||||||
c.noise(j, j + 1000, j * j);
|
c.noise(j, j + 1000, j * j);
|
||||||
c.noise(j, -j);
|
c.noise(j, -j);
|
||||||
}
|
}
|
||||||
|
|
||||||
PrecisionStopwatch px = PrecisionStopwatch.start();
|
PrecisionStopwatch px = PrecisionStopwatch.start();
|
||||||
|
|
||||||
for(int j = 0; j < 100000; j++) {
|
for (int j = 0; j < 100000; j++) {
|
||||||
c.noise(j, j + 1000, j * j);
|
c.noise(j, j + 1000, j * j);
|
||||||
c.noise(j, -j);
|
c.noise(j, -j);
|
||||||
}
|
}
|
||||||
@@ -470,7 +316,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
fileText.add("Noise Style Performance Impacts: ");
|
fileText.add("Noise Style Performance Impacts: ");
|
||||||
|
|
||||||
for(NoiseStyle i : styleTimings.sortKNumber()) {
|
for (NoiseStyle i : styleTimings.sortKNumber()) {
|
||||||
fileText.add(i.name() + ": " + styleTimings.get(i));
|
fileText.add(i.name() + ": " + styleTimings.get(i));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -478,20 +324,20 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
sender().sendMessage("Calculating Interpolator Timings...");
|
sender().sendMessage("Calculating Interpolator Timings...");
|
||||||
|
|
||||||
for(InterpolationMethod i : InterpolationMethod.values()) {
|
for (InterpolationMethod i : InterpolationMethod.values()) {
|
||||||
IrisInterpolator in = new IrisInterpolator();
|
IrisInterpolator in = new IrisInterpolator();
|
||||||
in.setFunction(i);
|
in.setFunction(i);
|
||||||
in.setHorizontalScale(8);
|
in.setHorizontalScale(8);
|
||||||
|
|
||||||
NoiseProvider np = (x, z) -> Math.random();
|
NoiseProvider np = (x, z) -> Math.random();
|
||||||
|
|
||||||
for(int j = 0; j < 3000; j++) {
|
for (int j = 0; j < 3000; j++) {
|
||||||
in.interpolate(j, -j, np);
|
in.interpolate(j, -j, np);
|
||||||
}
|
}
|
||||||
|
|
||||||
PrecisionStopwatch px = PrecisionStopwatch.start();
|
PrecisionStopwatch px = PrecisionStopwatch.start();
|
||||||
|
|
||||||
for(int j = 0; j < 100000; j++) {
|
for (int j = 0; j < 100000; j++) {
|
||||||
in.interpolate(j + 10000, -j - 100000, np);
|
in.interpolate(j + 10000, -j - 100000, np);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -500,7 +346,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
fileText.add("Noise Interpolator Performance Impacts: ");
|
fileText.add("Noise Interpolator Performance Impacts: ");
|
||||||
|
|
||||||
for(InterpolationMethod i : interpolatorTimings.sortKNumber()) {
|
for (InterpolationMethod i : interpolatorTimings.sortKNumber()) {
|
||||||
fileText.add(i.name() + ": " + interpolatorTimings.get(i));
|
fileText.add(i.name() + ": " + interpolatorTimings.get(i));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -510,13 +356,13 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
KMap<String, KList<String>> btx = new KMap<>();
|
KMap<String, KList<String>> btx = new KMap<>();
|
||||||
|
|
||||||
for(String i : data.getGeneratorLoader().getPossibleKeys()) {
|
for (String i : data.getGeneratorLoader().getPossibleKeys()) {
|
||||||
KList<String> vv = new KList<>();
|
KList<String> vv = new KList<>();
|
||||||
IrisGenerator g = data.getGeneratorLoader().load(i);
|
IrisGenerator g = data.getGeneratorLoader().load(i);
|
||||||
KList<IrisNoiseGenerator> composites = g.getAllComposites();
|
KList<IrisNoiseGenerator> composites = g.getAllComposites();
|
||||||
double score = 0;
|
double score = 0;
|
||||||
int m = 0;
|
int m = 0;
|
||||||
for(IrisNoiseGenerator j : composites) {
|
for (IrisNoiseGenerator j : composites) {
|
||||||
m++;
|
m++;
|
||||||
score += styleTimings.get(j.getStyle().getStyle());
|
score += styleTimings.get(j.getStyle().getStyle());
|
||||||
vv.add("Composite Noise Style " + m + " " + j.getStyle().getStyle().name() + ": " + styleTimings.get(j.getStyle().getStyle()));
|
vv.add("Composite Noise Style " + m + " " + j.getStyle().getStyle().name() + ": " + styleTimings.get(j.getStyle().getStyle()));
|
||||||
@@ -530,7 +376,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
fileText.add("Project Generator Performance Impacts: ");
|
fileText.add("Project Generator Performance Impacts: ");
|
||||||
|
|
||||||
for(String i : generatorTimings.sortKNumber()) {
|
for (String i : generatorTimings.sortKNumber()) {
|
||||||
fileText.add(i + ": " + generatorTimings.get(i));
|
fileText.add(i + ": " + generatorTimings.get(i));
|
||||||
|
|
||||||
btx.get(i).forEach((ii) -> fileText.add(" " + ii));
|
btx.get(i).forEach((ii) -> fileText.add(" " + ii));
|
||||||
@@ -540,13 +386,13 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
KMap<String, KList<String>> bt = new KMap<>();
|
KMap<String, KList<String>> bt = new KMap<>();
|
||||||
|
|
||||||
for(String i : data.getBiomeLoader().getPossibleKeys()) {
|
for (String i : data.getBiomeLoader().getPossibleKeys()) {
|
||||||
KList<String> vv = new KList<>();
|
KList<String> vv = new KList<>();
|
||||||
IrisBiome b = data.getBiomeLoader().load(i);
|
IrisBiome b = data.getBiomeLoader().load(i);
|
||||||
double score = 0;
|
double score = 0;
|
||||||
|
|
||||||
int m = 0;
|
int m = 0;
|
||||||
for(IrisBiomePaletteLayer j : b.getLayers()) {
|
for (IrisBiomePaletteLayer j : b.getLayers()) {
|
||||||
m++;
|
m++;
|
||||||
score += styleTimings.get(j.getStyle().getStyle());
|
score += styleTimings.get(j.getStyle().getStyle());
|
||||||
vv.add("Palette Layer " + m + ": " + styleTimings.get(j.getStyle().getStyle()));
|
vv.add("Palette Layer " + m + ": " + styleTimings.get(j.getStyle().getStyle()));
|
||||||
@@ -562,7 +408,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
fileText.add("Project Biome Performance Impacts: ");
|
fileText.add("Project Biome Performance Impacts: ");
|
||||||
|
|
||||||
for(String i : biomeTimings.sortKNumber()) {
|
for (String i : biomeTimings.sortKNumber()) {
|
||||||
fileText.add(i + ": " + biomeTimings.get(i));
|
fileText.add(i + ": " + biomeTimings.get(i));
|
||||||
|
|
||||||
bt.get(i).forEach((ff) -> fileText.add(" " + ff));
|
bt.get(i).forEach((ff) -> fileText.add(" " + ff));
|
||||||
@@ -570,7 +416,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
fileText.add("");
|
fileText.add("");
|
||||||
|
|
||||||
for(String i : data.getRegionLoader().getPossibleKeys()) {
|
for (String i : data.getRegionLoader().getPossibleKeys()) {
|
||||||
IrisRegion b = data.getRegionLoader().load(i);
|
IrisRegion b = data.getRegionLoader().load(i);
|
||||||
double score = 0;
|
double score = 0;
|
||||||
|
|
||||||
@@ -581,25 +427,25 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
fileText.add("Project Region Performance Impacts: ");
|
fileText.add("Project Region Performance Impacts: ");
|
||||||
|
|
||||||
for(String i : regionTimings.sortKNumber()) {
|
for (String i : regionTimings.sortKNumber()) {
|
||||||
fileText.add(i + ": " + regionTimings.get(i));
|
fileText.add(i + ": " + regionTimings.get(i));
|
||||||
}
|
}
|
||||||
|
|
||||||
fileText.add("");
|
fileText.add("");
|
||||||
|
|
||||||
double m = 0;
|
double m = 0;
|
||||||
for(double i : biomeTimings.v()) {
|
for (double i : biomeTimings.v()) {
|
||||||
m += i;
|
m += i;
|
||||||
}
|
}
|
||||||
m /= biomeTimings.size();
|
m /= biomeTimings.size();
|
||||||
double mm = 0;
|
double mm = 0;
|
||||||
for(double i : generatorTimings.v()) {
|
for (double i : generatorTimings.v()) {
|
||||||
mm += i;
|
mm += i;
|
||||||
}
|
}
|
||||||
mm /= generatorTimings.size();
|
mm /= generatorTimings.size();
|
||||||
m += mm;
|
m += mm;
|
||||||
double mmm = 0;
|
double mmm = 0;
|
||||||
for(double i : regionTimings.v()) {
|
for (double i : regionTimings.v()) {
|
||||||
mmm += i;
|
mmm += i;
|
||||||
}
|
}
|
||||||
mmm /= regionTimings.size();
|
mmm /= regionTimings.size();
|
||||||
@@ -610,7 +456,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
IO.writeAll(report, fileText.toString("\n"));
|
IO.writeAll(report, fileText.toString("\n"));
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -618,30 +464,27 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
sender().sendMessage(C.GREEN + "Done! " + report.getPath());
|
sender().sendMessage(C.GREEN + "Done! " + report.getPath());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Decree(description = "Summon an Iris Entity", origin = DecreeOrigin.PLAYER)
|
@Decree(description = "Spawn an Iris entity", aliases = "summon", origin = DecreeOrigin.PLAYER)
|
||||||
public void summon(
|
public void spawn(
|
||||||
@Param(description = "The Iris Entity to spawn")
|
@Param(description = "The entity to spawn")
|
||||||
IrisEntity entity,
|
IrisEntity entity,
|
||||||
@Param(description = "The location at which to spawn the entity", defaultValue = "self")
|
@Param(description = "The location to spawn the entity at", contextual = true)
|
||||||
Vector location
|
Vector location
|
||||||
) {
|
) {
|
||||||
if(!sender().isPlayer()) {
|
if (!IrisToolbelt.isIrisWorld(player().getWorld())) {
|
||||||
sender().sendMessage(C.RED + "Players only (this is a config error. Ask support to add DecreeOrigin.PLAYER to the command you tried to run)");
|
sender().sendMessage(C.RED + "You have to be in an Iris world to spawn entities properly. Trying to spawn the best we can do.");
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
sender().sendMessage(C.GREEN + "Spawning entity");
|
|
||||||
entity.spawn(engine(), new Location(world(), location.getX(), location.getY(), location.getZ()));
|
entity.spawn(engine(), new Location(world(), location.getX(), location.getY(), location.getZ()));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Decree(description = "Teleport to the active studio world", aliases = "stp", origin = DecreeOrigin.PLAYER, sync = true)
|
@Decree(description = "Teleport to the active studio world", aliases = "stp", origin = DecreeOrigin.PLAYER, sync = true)
|
||||||
public void tpstudio() {
|
public void tpstudio() {
|
||||||
if(!Iris.service(StudioSVC.class).isProjectOpen()) {
|
if (!Iris.service(StudioSVC.class).isProjectOpen()) {
|
||||||
sender().sendMessage(C.RED + "No studio world is open!");
|
sender().sendMessage(C.RED + "No studio world is open!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(IrisToolbelt.isIrisWorld(world()) && engine().isStudio()) {
|
if (IrisToolbelt.isIrisWorld(world()) && engine().isStudio()) {
|
||||||
sender().sendMessage(C.RED + "You are already in a studio world!");
|
sender().sendMessage(C.RED + "You are already in a studio world!");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -653,11 +496,11 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(description = "Update your dimension projects VSCode workspace")
|
@Decree(description = "Update your dimension projects VSCode workspace")
|
||||||
public void update(
|
public void update(
|
||||||
@Param(description = "The dimension to update the workspace of", contextual = true, defaultValue = "default")
|
@Param(description = "The dimension to update the workspace of", contextual = true, defaultValue = "default")
|
||||||
IrisDimension dimension
|
IrisDimension dimension
|
||||||
) {
|
) {
|
||||||
sender().sendMessage(C.GOLD + "Updating Code Workspace for " + dimension.getName() + "...");
|
sender().sendMessage(C.GOLD + "Updating Code Workspace for " + dimension.getName() + "...");
|
||||||
if(new IrisProject(dimension.getLoader().getDataFolder()).updateWorkspace()) {
|
if (new IrisProject(dimension.getLoader().getDataFolder()).updateWorkspace()) {
|
||||||
sender().sendMessage(C.GREEN + "Updated Code Workspace for " + dimension.getName());
|
sender().sendMessage(C.GREEN + "Updated Code Workspace for " + dimension.getName());
|
||||||
} else {
|
} else {
|
||||||
sender().sendMessage(C.RED + "Invalid project: " + dimension.getName() + ". Try deleting the code-workspace file and try again.");
|
sender().sendMessage(C.RED + "Invalid project: " + dimension.getName() + ". Try deleting the code-workspace file and try again.");
|
||||||
@@ -666,14 +509,14 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
@Decree(aliases = "find-objects", description = "Get information about nearby structures")
|
@Decree(aliases = "find-objects", description = "Get information about nearby structures")
|
||||||
public void objects() {
|
public void objects() {
|
||||||
if(!IrisToolbelt.isIrisWorld(player().getWorld())) {
|
if (!IrisToolbelt.isIrisWorld(player().getWorld())) {
|
||||||
sender().sendMessage(C.RED + "You must be in an Iris world");
|
sender().sendMessage(C.RED + "You must be in an Iris world");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
World world = player().getWorld();
|
World world = player().getWorld();
|
||||||
|
|
||||||
if(!IrisToolbelt.isIrisWorld(world)) {
|
if (!IrisToolbelt.isIrisWorld(world)) {
|
||||||
sender().sendMessage("You must be in an iris world.");
|
sender().sendMessage("You must be in an iris world.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -687,7 +530,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
int cx = l.getChunk().getX();
|
int cx = l.getChunk().getX();
|
||||||
int cz = l.getChunk().getZ();
|
int cz = l.getChunk().getZ();
|
||||||
new Spiraler(3, 3, (x, z) -> chunks.addIfMissing(world.getChunkAt(x + cx, z + cz))).drain();
|
new Spiraler(3, 3, (x, z) -> chunks.addIfMissing(world.getChunkAt(x + cx, z + cz))).drain();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -705,7 +548,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
pw.println("Report Captured At: " + new Date());
|
pw.println("Report Captured At: " + new Date());
|
||||||
pw.println("Chunks: (" + chunks.size() + "): ");
|
pw.println("Chunks: (" + chunks.size() + "): ");
|
||||||
|
|
||||||
for(Chunk i : chunks) {
|
for (Chunk i : chunks) {
|
||||||
pw.println("- [" + i.getX() + ", " + i.getZ() + "]");
|
pw.println("- [" + i.getX() + ", " + i.getZ() + "]");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -714,19 +557,19 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
String age = "No idea...";
|
String age = "No idea...";
|
||||||
|
|
||||||
try {
|
try {
|
||||||
for(File i : Objects.requireNonNull(new File(world.getWorldFolder(), "region").listFiles())) {
|
for (File i : Objects.requireNonNull(new File(world.getWorldFolder(), "region").listFiles())) {
|
||||||
if(i.isFile()) {
|
if (i.isFile()) {
|
||||||
size += i.length();
|
size += i.length();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
FileTime creationTime = (FileTime) Files.getAttribute(world.getWorldFolder().toPath(), "creationTime");
|
FileTime creationTime = (FileTime) Files.getAttribute(world.getWorldFolder().toPath(), "creationTime");
|
||||||
age = hrf(Duration.of(M.ms() - creationTime.toMillis(), ChronoUnit.MILLIS));
|
age = hrf(Duration.of(M.ms() - creationTime.toMillis(), ChronoUnit.MILLIS));
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -734,10 +577,10 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
KList<String> caveBiomes = new KList<>();
|
KList<String> caveBiomes = new KList<>();
|
||||||
KMap<String, KMap<String, KList<String>>> objects = new KMap<>();
|
KMap<String, KMap<String, KList<String>>> objects = new KMap<>();
|
||||||
|
|
||||||
for(Chunk i : chunks) {
|
for (Chunk i : chunks) {
|
||||||
for(int j = 0; j < 16; j += 3) {
|
for (int j = 0; j < 16; j += 3) {
|
||||||
|
|
||||||
for(int k = 0; k < 16; k += 3) {
|
for (int k = 0; k < 16; k += 3) {
|
||||||
|
|
||||||
assert engine() != null;
|
assert engine() != null;
|
||||||
IrisBiome bb = engine().getSurfaceBiome((i.getX() * 16) + j, (i.getZ() * 16) + k);
|
IrisBiome bb = engine().getSurfaceBiome((i.getX() * 16) + j, (i.getZ() * 16) + k);
|
||||||
@@ -764,20 +607,20 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
pw.println("== Biome Info ==");
|
pw.println("== Biome Info ==");
|
||||||
pw.println("Found " + biomes.size() + " Biome(s): ");
|
pw.println("Found " + biomes.size() + " Biome(s): ");
|
||||||
|
|
||||||
for(String i : biomes) {
|
for (String i : biomes) {
|
||||||
pw.println("- " + i);
|
pw.println("- " + i);
|
||||||
}
|
}
|
||||||
pw.println();
|
pw.println();
|
||||||
|
|
||||||
pw.println("== Object Info ==");
|
pw.println("== Object Info ==");
|
||||||
|
|
||||||
for(String i : objects.k()) {
|
for (String i : objects.k()) {
|
||||||
pw.println("- " + i);
|
pw.println("- " + i);
|
||||||
|
|
||||||
for(String j : objects.get(i).k()) {
|
for (String j : objects.get(i).k()) {
|
||||||
pw.println(" @ " + j);
|
pw.println(" @ " + j);
|
||||||
|
|
||||||
for(String k : objects.get(i).get(j)) {
|
for (String k : objects.get(i).get(j)) {
|
||||||
pw.println(" * " + k);
|
pw.println(" * " + k);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -787,7 +630,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
pw.close();
|
pw.close();
|
||||||
|
|
||||||
sender().sendMessage("Reported to: " + ff.getPath());
|
sender().sendMessage("Reported to: " + ff.getPath());
|
||||||
} catch(FileNotFoundException e) {
|
} catch (FileNotFoundException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
@@ -797,15 +640,15 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
String n1 = bb.getName() + " [" + Form.capitalize(bb.getInferredType().name().toLowerCase()) + "] " + " (" + bb.getLoadFile().getName() + ")";
|
String n1 = bb.getName() + " [" + Form.capitalize(bb.getInferredType().name().toLowerCase()) + "] " + " (" + bb.getLoadFile().getName() + ")";
|
||||||
int m = 0;
|
int m = 0;
|
||||||
KSet<String> stop = new KSet<>();
|
KSet<String> stop = new KSet<>();
|
||||||
for(IrisObjectPlacement f : bb.getObjects()) {
|
for (IrisObjectPlacement f : bb.getObjects()) {
|
||||||
m++;
|
m++;
|
||||||
String n2 = "Placement #" + m + " (" + f.getPlace().size() + " possible objects)";
|
String n2 = "Placement #" + m + " (" + f.getPlace().size() + " possible objects)";
|
||||||
|
|
||||||
for(String i : f.getPlace()) {
|
for (String i : f.getPlace()) {
|
||||||
String nn3 = i + ": [ERROR] Failed to find object!";
|
String nn3 = i + ": [ERROR] Failed to find object!";
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if(stop.contains(i)) {
|
if (stop.contains(i)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -813,13 +656,13 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
BlockVector sz = IrisObject.sampleSize(ff);
|
BlockVector sz = IrisObject.sampleSize(ff);
|
||||||
nn3 = i + ": size=[" + sz.getBlockX() + "," + sz.getBlockY() + "," + sz.getBlockZ() + "] location=[" + ff.getPath() + "]";
|
nn3 = i + ": size=[" + sz.getBlockX() + "," + sz.getBlockY() + "," + sz.getBlockZ() + "] location=[" + ff.getPath() + "]";
|
||||||
stop.add(i);
|
stop.add(i);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
String n3 = nn3;
|
String n3 = nn3;
|
||||||
objects.computeIfAbsent(n1, (k1) -> new KMap<>())
|
objects.computeIfAbsent(n1, (k1) -> new KMap<>())
|
||||||
.computeIfAbsent(n2, (k) -> new KList<>()).addIfMissing(n3);
|
.computeIfAbsent(n2, (k) -> new KList<>()).addIfMissing(n3);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -828,7 +671,7 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
* @return true if server GUIs are not enabled
|
* @return true if server GUIs are not enabled
|
||||||
*/
|
*/
|
||||||
private boolean noGUI() {
|
private boolean noGUI() {
|
||||||
if(!IrisSettings.get().getGui().isUseServerLaunchedGuis()) {
|
if (!IrisSettings.get().getGui().isUseServerLaunchedGuis()) {
|
||||||
sender().sendMessage(C.RED + "You must have server launched GUIs enabled in the settings!");
|
sender().sendMessage(C.RED + "You must have server launched GUIs enabled in the settings!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -839,15 +682,15 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
* @return true if no studio is open or the player is not in one
|
* @return true if no studio is open or the player is not in one
|
||||||
*/
|
*/
|
||||||
private boolean noStudio() {
|
private boolean noStudio() {
|
||||||
if(!sender().isPlayer()) {
|
if (!sender().isPlayer()) {
|
||||||
sender().sendMessage(C.RED + "Players only!");
|
sender().sendMessage(C.RED + "Players only!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if(!Iris.service(StudioSVC.class).isProjectOpen()) {
|
if (!Iris.service(StudioSVC.class).isProjectOpen()) {
|
||||||
sender().sendMessage(C.RED + "No studio world is open!");
|
sender().sendMessage(C.RED + "No studio world is open!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if(!engine().isStudio()) {
|
if (!engine().isStudio()) {
|
||||||
sender().sendMessage(C.RED + "You must be in a studio world!");
|
sender().sendMessage(C.RED + "You must be in a studio world!");
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -856,14 +699,14 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
|
|
||||||
|
|
||||||
public void files(File clean, KList<File> files) {
|
public void files(File clean, KList<File> files) {
|
||||||
if(clean.isDirectory()) {
|
if (clean.isDirectory()) {
|
||||||
for(File i : clean.listFiles()) {
|
for (File i : clean.listFiles()) {
|
||||||
files(i, files);
|
files(i, files);
|
||||||
}
|
}
|
||||||
} else if(clean.getName().endsWith(".json")) {
|
} else if (clean.getName().endsWith(".json")) {
|
||||||
try {
|
try {
|
||||||
files.add(clean);
|
files.add(clean);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.error("Failed to beautify " + clean.getAbsolutePath() + " You may have errors in your json!");
|
Iris.error("Failed to beautify " + clean.getAbsolutePath() + " You may have errors in your json!");
|
||||||
}
|
}
|
||||||
@@ -871,28 +714,28 @@ public class CommandStudio implements DecreeExecutor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void fixBlocks(JSONObject obj) {
|
private void fixBlocks(JSONObject obj) {
|
||||||
for(String i : obj.keySet()) {
|
for (String i : obj.keySet()) {
|
||||||
Object o = obj.get(i);
|
Object o = obj.get(i);
|
||||||
|
|
||||||
if(i.equals("block") && o instanceof String && !o.toString().trim().isEmpty() && !o.toString().contains(":")) {
|
if (i.equals("block") && o instanceof String && !o.toString().trim().isEmpty() && !o.toString().contains(":")) {
|
||||||
obj.put(i, "minecraft:" + o);
|
obj.put(i, "minecraft:" + o);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(o instanceof JSONObject) {
|
if (o instanceof JSONObject) {
|
||||||
fixBlocks((JSONObject) o);
|
fixBlocks((JSONObject) o);
|
||||||
} else if(o instanceof JSONArray) {
|
} else if (o instanceof JSONArray) {
|
||||||
fixBlocks((JSONArray) o);
|
fixBlocks((JSONArray) o);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void fixBlocks(JSONArray obj) {
|
private void fixBlocks(JSONArray obj) {
|
||||||
for(int i = 0; i < obj.length(); i++) {
|
for (int i = 0; i < obj.length(); i++) {
|
||||||
Object o = obj.get(i);
|
Object o = obj.get(i);
|
||||||
|
|
||||||
if(o instanceof JSONObject) {
|
if (o instanceof JSONObject) {
|
||||||
fixBlocks((JSONObject) o);
|
fixBlocks((JSONObject) o);
|
||||||
} else if(o instanceof JSONArray) {
|
} else if (o instanceof JSONArray) {
|
||||||
fixBlocks((JSONArray) o);
|
fixBlocks((JSONArray) o);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -45,16 +45,16 @@ public class CommandWhat implements DecreeExecutor {
|
|||||||
public void hand() {
|
public void hand() {
|
||||||
try {
|
try {
|
||||||
BlockData bd = player().getInventory().getItemInMainHand().getType().createBlockData();
|
BlockData bd = player().getInventory().getItemInMainHand().getType().createBlockData();
|
||||||
if(!bd.getMaterial().equals(Material.AIR)) {
|
if (!bd.getMaterial().equals(Material.AIR)) {
|
||||||
sender().sendMessage("Material: " + C.GREEN + bd.getMaterial().name());
|
sender().sendMessage("Material: " + C.GREEN + bd.getMaterial().name());
|
||||||
sender().sendMessage("Full: " + C.WHITE + bd.getAsString(true));
|
sender().sendMessage("Full: " + C.WHITE + bd.getAsString(true));
|
||||||
} else {
|
} else {
|
||||||
sender().sendMessage("Please hold a block/item");
|
sender().sendMessage("Please hold a block/item");
|
||||||
}
|
}
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Material bd = player().getInventory().getItemInMainHand().getType();
|
Material bd = player().getInventory().getItemInMainHand().getType();
|
||||||
if(!bd.equals(Material.AIR)) {
|
if (!bd.equals(Material.AIR)) {
|
||||||
sender().sendMessage("Material: " + C.GREEN + bd.name());
|
sender().sendMessage("Material: " + C.GREEN + bd.name());
|
||||||
} else {
|
} else {
|
||||||
sender().sendMessage("Please hold a block/item");
|
sender().sendMessage("Please hold a block/item");
|
||||||
@@ -65,17 +65,17 @@ public class CommandWhat implements DecreeExecutor {
|
|||||||
@Decree(description = "What biome am i in?", origin = DecreeOrigin.PLAYER)
|
@Decree(description = "What biome am i in?", origin = DecreeOrigin.PLAYER)
|
||||||
public void biome() {
|
public void biome() {
|
||||||
try {
|
try {
|
||||||
IrisBiome b = engine().getBiome(player().getLocation().getBlockX(), player().getLocation().getBlockY(), player().getLocation().getBlockZ());
|
IrisBiome b = engine().getBiome(player().getLocation().getBlockX(), player().getLocation().getBlockY() - player().getWorld().getMinHeight(), player().getLocation().getBlockZ());
|
||||||
sender().sendMessage("IBiome: " + b.getLoadKey() + " (" + b.getDerivative().name() + ")");
|
sender().sendMessage("IBiome: " + b.getLoadKey() + " (" + b.getDerivative().name() + ")");
|
||||||
|
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage("Non-Iris Biome: " + player().getLocation().getBlock().getBiome().name());
|
sender().sendMessage("Non-Iris Biome: " + player().getLocation().getBlock().getBiome().name());
|
||||||
|
|
||||||
if(player().getLocation().getBlock().getBiome().equals(Biome.CUSTOM)) {
|
if (player().getLocation().getBlock().getBiome().equals(Biome.CUSTOM)) {
|
||||||
try {
|
try {
|
||||||
sender().sendMessage("Data Pack Biome: " + INMS.get().getTrueBiomeBaseKey(player().getLocation()) + " (ID: " + INMS.get().getTrueBiomeBaseId(INMS.get().getTrueBiomeBase(player().getLocation())) + ")");
|
sender().sendMessage("Data Pack Biome: " + INMS.get().getTrueBiomeBaseKey(player().getLocation()) + " (ID: " + INMS.get().getTrueBiomeBaseId(INMS.get().getTrueBiomeBase(player().getLocation())) + ")");
|
||||||
} catch(Throwable ee) {
|
} catch (Throwable ee) {
|
||||||
Iris.reportError(ee);
|
Iris.reportError(ee);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -87,41 +87,41 @@ public class CommandWhat implements DecreeExecutor {
|
|||||||
BlockData bd;
|
BlockData bd;
|
||||||
try {
|
try {
|
||||||
bd = player().getTargetBlockExact(128, FluidCollisionMode.NEVER).getBlockData();
|
bd = player().getTargetBlockExact(128, FluidCollisionMode.NEVER).getBlockData();
|
||||||
} catch(NullPointerException e) {
|
} catch (NullPointerException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
sender().sendMessage("Please look at any block, not at the sky");
|
sender().sendMessage("Please look at any block, not at the sky");
|
||||||
bd = null;
|
bd = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(bd != null) {
|
if (bd != null) {
|
||||||
sender().sendMessage("Material: " + C.GREEN + bd.getMaterial().name());
|
sender().sendMessage("Material: " + C.GREEN + bd.getMaterial().name());
|
||||||
sender().sendMessage("Full: " + C.WHITE + bd.getAsString(true));
|
sender().sendMessage("Full: " + C.WHITE + bd.getAsString(true));
|
||||||
|
|
||||||
if(B.isStorage(bd)) {
|
if (B.isStorage(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Storage Block (Loot Capable)");
|
sender().sendMessage(C.YELLOW + "* Storage Block (Loot Capable)");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(B.isLit(bd)) {
|
if (B.isLit(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Lit Block (Light Capable)");
|
sender().sendMessage(C.YELLOW + "* Lit Block (Light Capable)");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(B.isFoliage(bd)) {
|
if (B.isFoliage(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Foliage Block");
|
sender().sendMessage(C.YELLOW + "* Foliage Block");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(B.isDecorant(bd)) {
|
if (B.isDecorant(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Decorant Block");
|
sender().sendMessage(C.YELLOW + "* Decorant Block");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(B.isFluid(bd)) {
|
if (B.isFluid(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Fluid Block");
|
sender().sendMessage(C.YELLOW + "* Fluid Block");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(B.isFoliagePlantable(bd)) {
|
if (B.isFoliagePlantable(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Plantable Foliage Block");
|
sender().sendMessage(C.YELLOW + "* Plantable Foliage Block");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(B.isSolid(bd)) {
|
if (B.isSolid(bd)) {
|
||||||
sender().sendMessage(C.YELLOW + "* Solid Block");
|
sender().sendMessage(C.YELLOW + "* Solid Block");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -131,17 +131,17 @@ public class CommandWhat implements DecreeExecutor {
|
|||||||
public void markers(@Param(description = "Marker name such as cave_floor or cave_ceiling") String marker) {
|
public void markers(@Param(description = "Marker name such as cave_floor or cave_ceiling") String marker) {
|
||||||
Chunk c = player().getLocation().getChunk();
|
Chunk c = player().getLocation().getChunk();
|
||||||
|
|
||||||
if(IrisToolbelt.isIrisWorld(c.getWorld())) {
|
if (IrisToolbelt.isIrisWorld(c.getWorld())) {
|
||||||
int m = 1;
|
int m = 1;
|
||||||
AtomicInteger v = new AtomicInteger(0);
|
AtomicInteger v = new AtomicInteger(0);
|
||||||
|
|
||||||
for(int xxx = c.getX() - 4; xxx <= c.getX() + 4; xxx++) {
|
for (int xxx = c.getX() - 4; xxx <= c.getX() + 4; xxx++) {
|
||||||
for(int zzz = c.getZ() - 4; zzz <= c.getZ() + 4; zzz++) {
|
for (int zzz = c.getZ() - 4; zzz <= c.getZ() + 4; zzz++) {
|
||||||
IrisToolbelt.access(c.getWorld()).getEngine().getMantle().findMarkers(xxx, zzz, new MatterMarker(marker))
|
IrisToolbelt.access(c.getWorld()).getEngine().getMantle().findMarkers(xxx, zzz, new MatterMarker(marker))
|
||||||
.convert((i) -> i.toLocation(c.getWorld())).forEach((i) -> {
|
.convert((i) -> i.toLocation(c.getWorld())).forEach((i) -> {
|
||||||
J.s(() -> BlockSignal.of(i.getBlock(), 100));
|
J.s(() -> BlockSignal.of(i.getBlock(), 100));
|
||||||
v.incrementAndGet();
|
v.incrementAndGet();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -51,7 +51,7 @@ public class BlockSignal {
|
|||||||
active.decrementAndGet();
|
active.decrementAndGet();
|
||||||
BlockData type = block.getBlockData();
|
BlockData type = block.getBlockData();
|
||||||
MultiBurst.burst.lazy(() -> {
|
MultiBurst.burst.lazy(() -> {
|
||||||
for(Player i : block.getWorld().getPlayers()) {
|
for (Player i : block.getWorld().getPlayers()) {
|
||||||
i.sendBlockChange(block.getLocation(), block.getBlockData());
|
i.sendBlockChange(block.getLocation(), block.getBlockData());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -82,7 +82,7 @@ public class BlockSignal {
|
|||||||
new SR(20) {
|
new SR(20) {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
if(e.isDead()) {
|
if (e.isDead()) {
|
||||||
cancel();
|
cancel();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -98,7 +98,7 @@ public class BlockSignal {
|
|||||||
BlockData type = block.getBlockData();
|
BlockData type = block.getBlockData();
|
||||||
|
|
||||||
MultiBurst.burst.lazy(() -> {
|
MultiBurst.burst.lazy(() -> {
|
||||||
for(Player i : block.getWorld().getPlayers()) {
|
for (Player i : block.getWorld().getPlayers()) {
|
||||||
i.sendBlockChange(block.getLocation(), block.getBlockData());
|
i.sendBlockChange(block.getLocation(), block.getBlockData());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -50,11 +50,11 @@ public class DustRevealer {
|
|||||||
|
|
||||||
J.s(() -> {
|
J.s(() -> {
|
||||||
new BlockSignal(world.getBlockAt(block.getX(), block.getY(), block.getZ()), 10);
|
new BlockSignal(world.getBlockAt(block.getX(), block.getY(), block.getZ()), 10);
|
||||||
if(M.r(0.25)) {
|
if (M.r(0.25)) {
|
||||||
world.playSound(block.toBlock(world).getLocation(), Sound.BLOCK_AMETHYST_BLOCK_CHIME, 1f, RNG.r.f(0.2f, 2f));
|
world.playSound(block.toBlock(world).getLocation(), Sound.BLOCK_AMETHYST_BLOCK_CHIME, 1f, RNG.r.f(0.2f, 2f));
|
||||||
}
|
}
|
||||||
J.a(() -> {
|
J.a(() -> {
|
||||||
while(BlockSignal.active.get() > 128) {
|
while (BlockSignal.active.get() > 128) {
|
||||||
J.sleep(5);
|
J.sleep(5);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -85,7 +85,7 @@ public class DustRevealer {
|
|||||||
is(new BlockPosition(block.getX() + 1, block.getY() + 1, block.getZ() + 1));
|
is(new BlockPosition(block.getX() + 1, block.getY() + 1, block.getZ() + 1));
|
||||||
is(new BlockPosition(block.getX() + 1, block.getY() - 1, block.getZ() - 1));
|
is(new BlockPosition(block.getX() + 1, block.getY() - 1, block.getZ() - 1));
|
||||||
is(new BlockPosition(block.getX() + 1, block.getY() - 1, block.getZ() + 1));
|
is(new BlockPosition(block.getX() + 1, block.getY() - 1, block.getZ() + 1));
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -97,9 +97,9 @@ public class DustRevealer {
|
|||||||
World world = block.getWorld();
|
World world = block.getWorld();
|
||||||
Engine access = IrisToolbelt.access(world).getEngine();
|
Engine access = IrisToolbelt.access(world).getEngine();
|
||||||
|
|
||||||
if(access != null) {
|
if (access != null) {
|
||||||
String a = access.getObjectPlacementKey(block.getX(), block.getY() - block.getWorld().getMinHeight(), block.getZ());
|
String a = access.getObjectPlacementKey(block.getX(), block.getY() - block.getWorld().getMinHeight(), block.getZ());
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
world.playSound(block.getLocation(), Sound.ITEM_LODESTONE_COMPASS_LOCK, 1f, 0.1f);
|
world.playSound(block.getLocation(), Sound.ITEM_LODESTONE_COMPASS_LOCK, 1f, 0.1f);
|
||||||
|
|
||||||
sender.sendMessage("Found object " + a);
|
sender.sendMessage("Found object " + a);
|
||||||
@@ -112,7 +112,7 @@ public class DustRevealer {
|
|||||||
|
|
||||||
private boolean is(BlockPosition a) {
|
private boolean is(BlockPosition a) {
|
||||||
int betterY = a.getY() - world.getMinHeight();
|
int betterY = a.getY() - world.getMinHeight();
|
||||||
if(isValidTry(a) && engine.getObjectPlacementKey(a.getX(), betterY, a.getZ()) != null && engine.getObjectPlacementKey(a.getX(), betterY, a.getZ()).equals(key)) {
|
if (isValidTry(a) && engine.getObjectPlacementKey(a.getX(), betterY, a.getZ()) != null && engine.getObjectPlacementKey(a.getX(), betterY, a.getZ()).equals(key)) {
|
||||||
hits.add(a);
|
hits.add(a);
|
||||||
new DustRevealer(engine, world, a, key, hits);
|
new DustRevealer(engine, world, a, key, hits);
|
||||||
return true;
|
return true;
|
||||||
|
|||||||
@@ -19,14 +19,9 @@
|
|||||||
package com.volmit.iris.core.edit;
|
package com.volmit.iris.core.edit;
|
||||||
|
|
||||||
import com.google.gson.Gson;
|
import com.google.gson.Gson;
|
||||||
import com.google.gson.JsonObject;
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.service.WandSVC;
|
import com.volmit.iris.core.service.WandSVC;
|
||||||
import com.volmit.iris.engine.object.IrisDirection;
|
import com.volmit.iris.engine.object.*;
|
||||||
import com.volmit.iris.engine.object.IrisJigsawPiece;
|
|
||||||
import com.volmit.iris.engine.object.IrisJigsawPieceConnector;
|
|
||||||
import com.volmit.iris.engine.object.IrisObject;
|
|
||||||
import com.volmit.iris.engine.object.IrisPosition;
|
|
||||||
import com.volmit.iris.util.collection.KList;
|
import com.volmit.iris.util.collection.KList;
|
||||||
import com.volmit.iris.util.collection.KMap;
|
import com.volmit.iris.util.collection.KMap;
|
||||||
import com.volmit.iris.util.data.Cuboid;
|
import com.volmit.iris.util.data.Cuboid;
|
||||||
@@ -66,13 +61,12 @@ public class JigsawEditor implements Listener {
|
|||||||
private Location target;
|
private Location target;
|
||||||
|
|
||||||
public JigsawEditor(Player player, IrisJigsawPiece piece, IrisObject object, File saveLocation) {
|
public JigsawEditor(Player player, IrisJigsawPiece piece, IrisObject object, File saveLocation) {
|
||||||
if(editors.containsKey(player)) {
|
if (editors.containsKey(player)) {
|
||||||
editors.get(player).close();
|
editors.get(player).close();
|
||||||
}
|
}
|
||||||
|
|
||||||
editors.put(player, this);
|
editors.put(player, this);
|
||||||
if(object == null)
|
if (object == null) {
|
||||||
{
|
|
||||||
throw new RuntimeException("Object is null! " + piece.getObject());
|
throw new RuntimeException("Object is null! " + piece.getObject());
|
||||||
}
|
}
|
||||||
this.object = object;
|
this.object = object;
|
||||||
@@ -90,20 +84,20 @@ public class JigsawEditor implements Listener {
|
|||||||
|
|
||||||
@EventHandler
|
@EventHandler
|
||||||
public void on(PlayerMoveEvent e) {
|
public void on(PlayerMoveEvent e) {
|
||||||
if(e.getPlayer().equals(player)) {
|
if (e.getPlayer().equals(player)) {
|
||||||
try {
|
try {
|
||||||
target = player.getTargetBlockExact(7).getLocation();
|
target = player.getTargetBlockExact(7).getLocation();
|
||||||
} catch(Throwable ex) {
|
} catch (Throwable ex) {
|
||||||
Iris.reportError(ex);
|
Iris.reportError(ex);
|
||||||
target = player.getLocation();
|
target = player.getLocation();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(cuboid.contains(target)) {
|
if (cuboid.contains(target)) {
|
||||||
for(IrisPosition i : falling.k()) {
|
for (IrisPosition i : falling.k()) {
|
||||||
Location at = toLocation(i);
|
Location at = toLocation(i);
|
||||||
|
|
||||||
if(at.equals(target)) {
|
if (at.equals(target)) {
|
||||||
falling.remove(i).run();
|
falling.remove(i).run();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -113,43 +107,43 @@ public class JigsawEditor implements Listener {
|
|||||||
|
|
||||||
public Location toLocation(IrisPosition i) {
|
public Location toLocation(IrisPosition i) {
|
||||||
return origin.clone()
|
return origin.clone()
|
||||||
.add(new Vector(i.getX(), i.getY(), i.getZ()))
|
.add(new Vector(i.getX(), i.getY(), i.getZ()))
|
||||||
.add(object.getCenter())
|
.add(object.getCenter())
|
||||||
.getBlock()
|
.getBlock()
|
||||||
.getLocation();
|
.getLocation();
|
||||||
}
|
}
|
||||||
|
|
||||||
public IrisPosition toPosition(Location l) {
|
public IrisPosition toPosition(Location l) {
|
||||||
return new IrisPosition(l.clone().getBlock().getLocation()
|
return new IrisPosition(l.clone().getBlock().getLocation()
|
||||||
.subtract(origin.clone())
|
.subtract(origin.clone())
|
||||||
.subtract(object.getCenter())
|
.subtract(object.getCenter())
|
||||||
.add(1, 1, 1)
|
.add(1, 1, 1)
|
||||||
.toVector());
|
.toVector());
|
||||||
}
|
}
|
||||||
|
|
||||||
@EventHandler
|
@EventHandler
|
||||||
public void on(PlayerInteractEvent e) {
|
public void on(PlayerInteractEvent e) {
|
||||||
if(e.getAction().equals(Action.RIGHT_CLICK_BLOCK)) {
|
if (e.getAction().equals(Action.RIGHT_CLICK_BLOCK)) {
|
||||||
if(e.getClickedBlock() != null && cuboid.contains(e.getClickedBlock().getLocation()) && e.getPlayer().equals(player)) {
|
if (e.getClickedBlock() != null && cuboid.contains(e.getClickedBlock().getLocation()) && e.getPlayer().equals(player)) {
|
||||||
IrisPosition pos = toPosition(e.getClickedBlock().getLocation());
|
IrisPosition pos = toPosition(e.getClickedBlock().getLocation());
|
||||||
IrisJigsawPieceConnector connector = null;
|
IrisJigsawPieceConnector connector = null;
|
||||||
for(IrisJigsawPieceConnector i : piece.getConnectors()) {
|
for (IrisJigsawPieceConnector i : piece.getConnectors()) {
|
||||||
if(i.getPosition().equals(pos)) {
|
if (i.getPosition().equals(pos)) {
|
||||||
connector = i;
|
connector = i;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!player.isSneaking() && connector == null) {
|
if (!player.isSneaking() && connector == null) {
|
||||||
connector = new IrisJigsawPieceConnector();
|
connector = new IrisJigsawPieceConnector();
|
||||||
connector.setDirection(IrisDirection.getDirection(e.getBlockFace()));
|
connector.setDirection(IrisDirection.getDirection(e.getBlockFace()));
|
||||||
connector.setPosition(pos);
|
connector.setPosition(pos);
|
||||||
piece.getConnectors().add(connector);
|
piece.getConnectors().add(connector);
|
||||||
player.playSound(e.getClickedBlock().getLocation(), Sound.ENTITY_ITEM_FRAME_ADD_ITEM, 1f, 1f);
|
player.playSound(e.getClickedBlock().getLocation(), Sound.ENTITY_ITEM_FRAME_ADD_ITEM, 1f, 1f);
|
||||||
} else if(player.isSneaking() && connector != null) {
|
} else if (player.isSneaking() && connector != null) {
|
||||||
piece.getConnectors().remove(connector);
|
piece.getConnectors().remove(connector);
|
||||||
player.playSound(e.getClickedBlock().getLocation(), Sound.ENTITY_ITEM_FRAME_REMOVE_ITEM, 1f, 1f);
|
player.playSound(e.getClickedBlock().getLocation(), Sound.ENTITY_ITEM_FRAME_REMOVE_ITEM, 1f, 1f);
|
||||||
} else if(connector != null && !player.isSneaking()) {
|
} else if (connector != null && !player.isSneaking()) {
|
||||||
connector.setDirection(IrisDirection.getDirection(e.getBlockFace()));
|
connector.setDirection(IrisDirection.getDirection(e.getBlockFace()));
|
||||||
player.playSound(e.getClickedBlock().getLocation(), Sound.ENTITY_ITEM_FRAME_ROTATE_ITEM, 1f, 1f);
|
player.playSound(e.getClickedBlock().getLocation(), Sound.ENTITY_ITEM_FRAME_ROTATE_ITEM, 1f, 1f);
|
||||||
}
|
}
|
||||||
@@ -157,10 +151,8 @@ public class JigsawEditor implements Listener {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void removeKey(JSONObject o, String... path)
|
private void removeKey(JSONObject o, String... path) {
|
||||||
{
|
if (path.length == 1) {
|
||||||
if(path.length == 1)
|
|
||||||
{
|
|
||||||
o.remove(path[0]);
|
o.remove(path[0]);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -170,13 +162,11 @@ public class JigsawEditor implements Listener {
|
|||||||
removeKey(o.getJSONObject(path[0]), s.toArray(new String[0]));
|
removeKey(o.getJSONObject(path[0]), s.toArray(new String[0]));
|
||||||
}
|
}
|
||||||
|
|
||||||
private List<JSONObject> getObjectsInArray(JSONObject a, String key)
|
private List<JSONObject> getObjectsInArray(JSONObject a) { // This gets all the objects in an array that are connectors
|
||||||
{
|
|
||||||
KList<JSONObject> o = new KList<>();
|
KList<JSONObject> o = new KList<>();
|
||||||
|
|
||||||
for(int i = 0; i < a.getJSONArray(key).length(); i++)
|
for (int i = 0; i < a.getJSONArray("connectors").length(); i++) {
|
||||||
{
|
o.add(a.getJSONArray("connectors").getJSONObject(i));
|
||||||
o.add(a.getJSONArray(key).getJSONObject(i));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return o;
|
return o;
|
||||||
@@ -192,16 +182,15 @@ public class JigsawEditor implements Listener {
|
|||||||
|
|
||||||
// remove root key
|
// remove root key
|
||||||
removeKey(j, "placementOptions"); // should work
|
removeKey(j, "placementOptions"); // should work
|
||||||
j.remove("placementOptions"); // otherwise
|
j.remove("placementOptions"); // otherwise
|
||||||
|
|
||||||
// Remove key in all objects in array
|
// Remove key in all objects in array
|
||||||
for(JSONObject i : getObjectsInArray(j, "connectors"))
|
for (JSONObject i : getObjectsInArray(j)) {
|
||||||
{
|
removeKey(i, "rotateConnector");
|
||||||
removeKey(i, "rotateConnector");
|
}
|
||||||
}
|
|
||||||
|
|
||||||
IO.writeAll(targetSaveLocation, j.toString(4));
|
IO.writeAll(targetSaveLocation, j.toString(4));
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -215,20 +204,20 @@ public class JigsawEditor implements Listener {
|
|||||||
object.unplaceCenterY(origin);
|
object.unplaceCenterY(origin);
|
||||||
falling.v().forEach(Runnable::run);
|
falling.v().forEach(Runnable::run);
|
||||||
}).get();
|
}).get();
|
||||||
} catch(InterruptedException | ExecutionException e) {
|
} catch (InterruptedException | ExecutionException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
editors.remove(player);
|
editors.remove(player);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void onTick() {
|
public void onTick() {
|
||||||
if(cl.flip()) {
|
if (cl.flip()) {
|
||||||
Iris.service(WandSVC.class).draw(cuboid, player);
|
Iris.service(WandSVC.class).draw(cuboid, player);
|
||||||
|
|
||||||
f:
|
f:
|
||||||
for(IrisPosition i : falling.k()) {
|
for (IrisPosition i : falling.k()) {
|
||||||
for(IrisJigsawPieceConnector j : piece.getConnectors()) {
|
for (IrisJigsawPieceConnector j : piece.getConnectors()) {
|
||||||
if(j.getPosition().equals(i)) {
|
if (j.getPosition().equals(i)) {
|
||||||
continue f;
|
continue f;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -236,23 +225,23 @@ public class JigsawEditor implements Listener {
|
|||||||
falling.remove(i).run();
|
falling.remove(i).run();
|
||||||
}
|
}
|
||||||
|
|
||||||
for(IrisJigsawPieceConnector i : piece.getConnectors()) {
|
for (IrisJigsawPieceConnector i : piece.getConnectors()) {
|
||||||
IrisPosition pos = i.getPosition();
|
IrisPosition pos = i.getPosition();
|
||||||
Location at = toLocation(pos);
|
Location at = toLocation(pos);
|
||||||
|
|
||||||
Vector dir = i.getDirection().toVector().clone();
|
Vector dir = i.getDirection().toVector().clone();
|
||||||
|
|
||||||
|
|
||||||
for(int ix = 0; ix < RNG.r.i(1, 3); ix++) {
|
for (int ix = 0; ix < RNG.r.i(1, 3); ix++) {
|
||||||
at.getWorld().spawnParticle(Particle.SOUL_FIRE_FLAME, at.clone().getBlock().getLocation().add(0.25, 0.25, 0.25).add(RNG.r.d(0.5), RNG.r.d(0.5), RNG.r.d(0.5)), 0, dir.getX(), dir.getY(), dir.getZ(), 0.092 + RNG.r.d(-0.03, 0.08));
|
at.getWorld().spawnParticle(Particle.SOUL_FIRE_FLAME, at.clone().getBlock().getLocation().add(0.25, 0.25, 0.25).add(RNG.r.d(0.5), RNG.r.d(0.5), RNG.r.d(0.5)), 0, dir.getX(), dir.getY(), dir.getZ(), 0.092 + RNG.r.d(-0.03, 0.08));
|
||||||
}
|
}
|
||||||
|
|
||||||
if(at.getBlock().getLocation().equals(target)) {
|
if (at.getBlock().getLocation().equals(target)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!falling.containsKey(pos)) {
|
if (!falling.containsKey(pos)) {
|
||||||
if(at.getBlock().getType().isAir()) {
|
if (at.getBlock().getType().isAir()) {
|
||||||
at.getBlock().setType(Material.STONE);
|
at.getBlock().setType(Material.STONE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -35,24 +35,9 @@ import org.bukkit.event.EventHandler;
|
|||||||
import org.bukkit.event.Listener;
|
import org.bukkit.event.Listener;
|
||||||
|
|
||||||
import javax.imageio.ImageIO;
|
import javax.imageio.ImageIO;
|
||||||
import javax.swing.JComboBox;
|
import javax.swing.*;
|
||||||
import javax.swing.JComponent;
|
import java.awt.*;
|
||||||
import javax.swing.JFrame;
|
import java.awt.event.*;
|
||||||
import javax.swing.JLayeredPane;
|
|
||||||
import javax.swing.JPanel;
|
|
||||||
import javax.swing.JViewport;
|
|
||||||
import java.awt.Color;
|
|
||||||
import java.awt.Dimension;
|
|
||||||
import java.awt.EventQueue;
|
|
||||||
import java.awt.Graphics;
|
|
||||||
import java.awt.Graphics2D;
|
|
||||||
import java.awt.Point;
|
|
||||||
import java.awt.Rectangle;
|
|
||||||
import java.awt.event.MouseAdapter;
|
|
||||||
import java.awt.event.MouseEvent;
|
|
||||||
import java.awt.event.MouseMotionListener;
|
|
||||||
import java.awt.event.MouseWheelEvent;
|
|
||||||
import java.awt.event.MouseWheelListener;
|
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
@@ -133,10 +118,10 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
frame.add(pane);
|
frame.add(pane);
|
||||||
File file = Iris.getCached("Iris Icon", "https://raw.githubusercontent.com/VolmitSoftware/Iris/master/icon.png");
|
File file = Iris.getCached("Iris Icon", "https://raw.githubusercontent.com/VolmitSoftware/Iris/master/icon.png");
|
||||||
|
|
||||||
if(file != null) {
|
if (file != null) {
|
||||||
try {
|
try {
|
||||||
frame.setIconImage(ImageIO.read(file));
|
frame.setIconImage(ImageIO.read(file));
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -148,7 +133,7 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
JFrame frame = new JFrame("Noise Explorer");
|
JFrame frame = new JFrame("Noise Explorer");
|
||||||
NoiseExplorerGUI nv = new NoiseExplorerGUI();
|
NoiseExplorerGUI nv = new NoiseExplorerGUI();
|
||||||
frame.setDefaultCloseOperation(JFrame.HIDE_ON_CLOSE);
|
frame.setDefaultCloseOperation(JFrame.HIDE_ON_CLOSE);
|
||||||
KList<String> li = new KList<>(NoiseStyle.values()).toStringList();
|
KList<String> li = new KList<>(NoiseStyle.values()).toStringList().sort();
|
||||||
combo = new JComboBox<>(li.toArray(new String[0]));
|
combo = new JComboBox<>(li.toArray(new String[0]));
|
||||||
combo.setSelectedItem("STATIC");
|
combo.setSelectedItem("STATIC");
|
||||||
combo.setFocusable(false);
|
combo.setFocusable(false);
|
||||||
@@ -167,10 +152,10 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
frame.add(pane);
|
frame.add(pane);
|
||||||
File file = Iris.getCached("Iris Icon", "https://raw.githubusercontent.com/VolmitSoftware/Iris/master/icon.png");
|
File file = Iris.getCached("Iris Icon", "https://raw.githubusercontent.com/VolmitSoftware/Iris/master/icon.png");
|
||||||
|
|
||||||
if(file != null) {
|
if (file != null) {
|
||||||
try {
|
try {
|
||||||
frame.setIconImage(ImageIO.read(file));
|
frame.setIconImage(ImageIO.read(file));
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -194,14 +179,14 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
|
|
||||||
@EventHandler
|
@EventHandler
|
||||||
public void on(IrisEngineHotloadEvent e) {
|
public void on(IrisEngineHotloadEvent e) {
|
||||||
if(generator != null)
|
if (generator != null)
|
||||||
generator = loader.get();
|
generator = loader.get();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void mouseWheelMoved(MouseWheelEvent e) {
|
public void mouseWheelMoved(MouseWheelEvent e) {
|
||||||
|
|
||||||
int notches = e.getWheelRotation();
|
int notches = e.getWheelRotation();
|
||||||
if(e.isControlDown()) {
|
if (e.isControlDown()) {
|
||||||
t = t + ((0.0025 * t) * notches);
|
t = t + ((0.0025 * t) * notches);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -212,51 +197,51 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void paint(Graphics g) {
|
public void paint(Graphics g) {
|
||||||
if(scale < ascale) {
|
if (scale < ascale) {
|
||||||
ascale -= Math.abs(scale - ascale) * 0.16;
|
ascale -= Math.abs(scale - ascale) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(scale > ascale) {
|
if (scale > ascale) {
|
||||||
ascale += Math.abs(ascale - scale) * 0.16;
|
ascale += Math.abs(ascale - scale) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(t < tz) {
|
if (t < tz) {
|
||||||
tz -= Math.abs(t - tz) * 0.29;
|
tz -= Math.abs(t - tz) * 0.29;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(t > tz) {
|
if (t > tz) {
|
||||||
tz += Math.abs(tz - t) * 0.29;
|
tz += Math.abs(tz - t) * 0.29;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ox < oxp) {
|
if (ox < oxp) {
|
||||||
oxp -= Math.abs(ox - oxp) * 0.16;
|
oxp -= Math.abs(ox - oxp) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ox > oxp) {
|
if (ox > oxp) {
|
||||||
oxp += Math.abs(oxp - ox) * 0.16;
|
oxp += Math.abs(oxp - ox) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(oz < ozp) {
|
if (oz < ozp) {
|
||||||
ozp -= Math.abs(oz - ozp) * 0.16;
|
ozp -= Math.abs(oz - ozp) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(oz > ozp) {
|
if (oz > ozp) {
|
||||||
ozp += Math.abs(ozp - oz) * 0.16;
|
ozp += Math.abs(ozp - oz) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(mx < mxx) {
|
if (mx < mxx) {
|
||||||
mxx -= Math.abs(mx - mxx) * 0.16;
|
mxx -= Math.abs(mx - mxx) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(mx > mxx) {
|
if (mx > mxx) {
|
||||||
mxx += Math.abs(mxx - mx) * 0.16;
|
mxx += Math.abs(mxx - mx) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(mz < mzz) {
|
if (mz < mzz) {
|
||||||
mzz -= Math.abs(mz - mzz) * 0.16;
|
mzz -= Math.abs(mz - mzz) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(mz > mzz) {
|
if (mz > mzz) {
|
||||||
mzz += Math.abs(mzz - mz) * 0.16;
|
mzz += Math.abs(mzz - mz) * 0.16;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -265,26 +250,26 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
accuracy = down ? accuracy * 4 : accuracy;
|
accuracy = down ? accuracy * 4 : accuracy;
|
||||||
int v = 1000;
|
int v = 1000;
|
||||||
|
|
||||||
if(g instanceof Graphics2D gg) {
|
if (g instanceof Graphics2D gg) {
|
||||||
|
|
||||||
if(getParent().getWidth() != w || getParent().getHeight() != h) {
|
if (getParent().getWidth() != w || getParent().getHeight() != h) {
|
||||||
w = getParent().getWidth();
|
w = getParent().getWidth();
|
||||||
h = getParent().getHeight();
|
h = getParent().getHeight();
|
||||||
img = null;
|
img = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(img == null) {
|
if (img == null) {
|
||||||
img = new BufferedImage(w / accuracy, h / accuracy, BufferedImage.TYPE_INT_RGB);
|
img = new BufferedImage(w / accuracy, h / accuracy, BufferedImage.TYPE_INT_RGB);
|
||||||
}
|
}
|
||||||
|
|
||||||
BurstExecutor e = gx.burst(w);
|
BurstExecutor e = gx.burst(w);
|
||||||
|
|
||||||
for(int x = 0; x < w / accuracy; x++) {
|
for (int x = 0; x < w / accuracy; x++) {
|
||||||
int xx = x;
|
int xx = x;
|
||||||
|
|
||||||
int finalAccuracy = accuracy;
|
int finalAccuracy = accuracy;
|
||||||
e.queue(() -> {
|
e.queue(() -> {
|
||||||
for(int z = 0; z < h / finalAccuracy; z++) {
|
for (int z = 0; z < h / finalAccuracy; z++) {
|
||||||
double n = generator != null ? generator.apply(((xx * finalAccuracy) * ascale) + oxp, ((z * finalAccuracy) * ascale) + ozp) : cng.noise(((xx * finalAccuracy) * ascale) + oxp, ((z * finalAccuracy) * ascale) + ozp);
|
double n = generator != null ? generator.apply(((xx * finalAccuracy) * ascale) + oxp, ((z * finalAccuracy) * ascale) + ozp) : cng.noise(((xx * finalAccuracy) * ascale) + oxp, ((z * finalAccuracy) * ascale) + ozp);
|
||||||
n = n > 1 ? 1 : n < 0 ? 0 : n;
|
n = n > 1 ? 1 : n < 0 ? 0 : n;
|
||||||
|
|
||||||
@@ -292,8 +277,7 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
Color color = colorMode ? Color.getHSBColor((float) (n), 1f - (float) (n * n * n * n * n * n), 1f - (float) n) : Color.getHSBColor(0f, 0f, (float) n);
|
Color color = colorMode ? Color.getHSBColor((float) (n), 1f - (float) (n * n * n * n * n * n), 1f - (float) n) : Color.getHSBColor(0f, 0f, (float) n);
|
||||||
int rgb = color.getRGB();
|
int rgb = color.getRGB();
|
||||||
img.setRGB(xx, z, rgb);
|
img.setRGB(xx, z, rgb);
|
||||||
} catch(Throwable xxx) {
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -308,15 +292,15 @@ public class NoiseExplorerGUI extends JPanel implements MouseWheelListener, List
|
|||||||
t += 1D;
|
t += 1D;
|
||||||
r.put(p.getMilliseconds());
|
r.put(p.getMilliseconds());
|
||||||
|
|
||||||
if(!isVisible()) {
|
if (!isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!getParent().isVisible()) {
|
if (!getParent().isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!getParent().getParent().isVisible()) {
|
if (!getParent().getParent().isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -35,12 +35,8 @@ import com.volmit.iris.util.math.Position2;
|
|||||||
import com.volmit.iris.util.scheduling.ChronoLatch;
|
import com.volmit.iris.util.scheduling.ChronoLatch;
|
||||||
import com.volmit.iris.util.scheduling.J;
|
import com.volmit.iris.util.scheduling.J;
|
||||||
|
|
||||||
import javax.swing.JFrame;
|
import javax.swing.*;
|
||||||
import javax.swing.JPanel;
|
import java.awt.*;
|
||||||
import java.awt.Color;
|
|
||||||
import java.awt.Font;
|
|
||||||
import java.awt.Graphics;
|
|
||||||
import java.awt.Graphics2D;
|
|
||||||
import java.awt.event.KeyEvent;
|
import java.awt.event.KeyEvent;
|
||||||
import java.awt.event.KeyListener;
|
import java.awt.event.KeyListener;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
@@ -66,24 +62,23 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
private final IrisPregenerator pregenerator;
|
private final IrisPregenerator pregenerator;
|
||||||
private final Position2 min;
|
private final Position2 min;
|
||||||
private final Position2 max;
|
private final Position2 max;
|
||||||
|
private final ChronoLatch cl = new ChronoLatch(TimeUnit.MINUTES.toMillis(1));
|
||||||
|
private final Engine engine;
|
||||||
private JFrame frame;
|
private JFrame frame;
|
||||||
private PregenRenderer renderer;
|
private PregenRenderer renderer;
|
||||||
private int rgc = 0;
|
private int rgc = 0;
|
||||||
private final ChronoLatch cl = new ChronoLatch(TimeUnit.MINUTES.toMillis(1));
|
|
||||||
private String[] info;
|
private String[] info;
|
||||||
private final Engine engine;
|
|
||||||
|
|
||||||
public PregeneratorJob(PregenTask task, PregeneratorMethod method, Engine engine) {
|
public PregeneratorJob(PregenTask task, PregeneratorMethod method, Engine engine) {
|
||||||
this.engine = engine;
|
this.engine = engine;
|
||||||
instance = this;
|
instance = this;
|
||||||
monitor = new MemoryMonitor(50);
|
monitor = new MemoryMonitor(50);
|
||||||
saving = false;
|
saving = false;
|
||||||
info = new String[] {"Initializing..."};
|
info = new String[]{"Initializing..."};
|
||||||
this.task = task;
|
this.task = task;
|
||||||
this.pregenerator = new IrisPregenerator(task, method, this);
|
this.pregenerator = new IrisPregenerator(task, method, this);
|
||||||
max = new Position2(0, 0);
|
max = new Position2(0, 0);
|
||||||
min = new Position2(0, 0);
|
min = new Position2(0, 0);
|
||||||
KList<Runnable> draw = new KList<>();
|
|
||||||
task.iterateRegions((xx, zz) -> {
|
task.iterateRegions((xx, zz) -> {
|
||||||
min.setX(Math.min(xx << 5, min.getX()));
|
min.setX(Math.min(xx << 5, min.getX()));
|
||||||
min.setZ(Math.min(zz << 5, min.getZ()));
|
min.setZ(Math.min(zz << 5, min.getZ()));
|
||||||
@@ -91,19 +86,15 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
max.setZ(Math.max((zz << 5) + 31, max.getZ()));
|
max.setZ(Math.max((zz << 5) + 31, max.getZ()));
|
||||||
});
|
});
|
||||||
|
|
||||||
if(IrisSettings.get().getGui().isUseServerLaunchedGuis()) {
|
if (IrisSettings.get().getGui().isUseServerLaunchedGuis()) {
|
||||||
open();
|
open();
|
||||||
}
|
}
|
||||||
|
|
||||||
J.a(this.pregenerator::start, 20);
|
J.a(this.pregenerator::start, 20);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Mantle getMantle() {
|
|
||||||
return pregenerator.getMantle();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static boolean shutdownInstance() {
|
public static boolean shutdownInstance() {
|
||||||
if(instance == null) {
|
if (instance == null) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -116,11 +107,11 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static boolean pauseResume() {
|
public static boolean pauseResume() {
|
||||||
if(instance == null) {
|
if (instance == null) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(isPaused()) {
|
if (isPaused()) {
|
||||||
instance.pregenerator.resume();
|
instance.pregenerator.resume();
|
||||||
} else {
|
} else {
|
||||||
instance.pregenerator.pause();
|
instance.pregenerator.pause();
|
||||||
@@ -129,7 +120,7 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static boolean isPaused() {
|
public static boolean isPaused() {
|
||||||
if(instance == null) {
|
if (instance == null) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -140,7 +131,7 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
String v = (c.startsWith("#") ? c : "#" + c).trim();
|
String v = (c.startsWith("#") ? c : "#" + c).trim();
|
||||||
try {
|
try {
|
||||||
return Color.decode(v);
|
return Color.decode(v);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.error("Error Parsing 'color', (" + c + ")");
|
Iris.error("Error Parsing 'color', (" + c + ")");
|
||||||
}
|
}
|
||||||
@@ -148,6 +139,10 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
return Color.RED;
|
return Color.RED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Mantle getMantle() {
|
||||||
|
return pregenerator.getMantle();
|
||||||
|
}
|
||||||
|
|
||||||
public PregeneratorJob onProgress(Consumer<Double> c) {
|
public PregeneratorJob onProgress(Consumer<Double> c) {
|
||||||
onProgress.add(c);
|
onProgress.add(c);
|
||||||
return this;
|
return this;
|
||||||
@@ -159,21 +154,19 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void drawRegion(int x, int z, Color color) {
|
public void drawRegion(int x, int z, Color color) {
|
||||||
J.a(() -> {
|
J.a(() -> PregenTask.iterateRegion(x, z, (xx, zz) -> {
|
||||||
PregenTask.iterateRegion(x, z, (xx, zz) -> {
|
draw(xx, zz, color);
|
||||||
draw(xx, zz, color);
|
J.sleep(3);
|
||||||
J.sleep(3);
|
}));
|
||||||
});
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void draw(int x, int z, Color color) {
|
public void draw(int x, int z, Color color) {
|
||||||
try {
|
try {
|
||||||
if(renderer != null && frame != null && frame.isVisible()) {
|
if (renderer != null && frame != null && frame.isVisible()) {
|
||||||
renderer.func.accept(new Position2(x, z), color);
|
renderer.func.accept(new Position2(x, z), color);
|
||||||
}
|
}
|
||||||
} catch(Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
Iris.error("Failed to draw pregen");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -191,8 +184,8 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
monitor.close();
|
monitor.close();
|
||||||
J.sleep(3000);
|
J.sleep(3000);
|
||||||
frame.setVisible(false);
|
frame.setVisible(false);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable ignored) {
|
||||||
|
Iris.error("Error closing pregen gui");
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -206,8 +199,7 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
renderer.l = new ReentrantLock();
|
renderer.l = new ReentrantLock();
|
||||||
renderer.frame = frame;
|
renderer.frame = frame;
|
||||||
renderer.job = this;
|
renderer.job = this;
|
||||||
renderer.func = (c, b) ->
|
renderer.func = (c, b) -> {
|
||||||
{
|
|
||||||
renderer.l.lock();
|
renderer.l.lock();
|
||||||
renderer.order.add(() -> renderer.draw(c, b, renderer.bg));
|
renderer.order.add(() -> renderer.draw(c, b, renderer.bg));
|
||||||
renderer.l.unlock();
|
renderer.l.unlock();
|
||||||
@@ -215,40 +207,36 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
frame.add(renderer);
|
frame.add(renderer);
|
||||||
frame.setSize(1000, 1000);
|
frame.setSize(1000, 1000);
|
||||||
frame.setVisible(true);
|
frame.setVisible(true);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable ignored) {
|
||||||
|
Iris.error("Error opening pregen gui");
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onTick(double chunksPerSecond, double chunksPerMinute, double regionsPerMinute, double percent, int generated, int totalChunks, int chunksRemaining, long eta, long elapsed, String method) {
|
public void onTick(double chunksPerSecond, double chunksPerMinute, double regionsPerMinute, double percent, int generated, int totalChunks, int chunksRemaining, long eta, long elapsed, String method) {
|
||||||
info = new String[] {
|
info = new String[]{
|
||||||
(paused() ? "PAUSED" : (saving ? "Saving... " : "Generating")) + " " + Form.f(generated) + " of " + Form.f(totalChunks) + " (" + Form.pc(percent, 0) + " Complete)",
|
(paused() ? "PAUSED" : (saving ? "Saving... " : "Generating")) + " " + Form.f(generated) + " of " + Form.f(totalChunks) + " (" + Form.pc(percent, 0) + " Complete)",
|
||||||
"Speed: " + Form.f(chunksPerSecond, 0) + " Chunks/s, " + Form.f(regionsPerMinute, 1) + " Regions/m, " + Form.f(chunksPerMinute, 0) + " Chunks/m",
|
"Speed: " + Form.f(chunksPerSecond, 0) + " Chunks/s, " + Form.f(regionsPerMinute, 1) + " Regions/m, " + Form.f(chunksPerMinute, 0) + " Chunks/m",
|
||||||
Form.duration(eta, 2) + " Remaining " + " (" + Form.duration(elapsed, 2) + " Elapsed)",
|
Form.duration(eta, 2) + " Remaining " + " (" + Form.duration(elapsed, 2) + " Elapsed)",
|
||||||
"Generation Method: " + method,
|
"Generation Method: " + method,
|
||||||
"Memory: " + Form.memSize(monitor.getUsedBytes(), 2) + " (" + Form.pc(monitor.getUsagePercent(), 0) + ") Pressure: " + Form.memSize(monitor.getPressure(), 0) + "/s",
|
"Memory: " + Form.memSize(monitor.getUsedBytes(), 2) + " (" + Form.pc(monitor.getUsagePercent(), 0) + ") Pressure: " + Form.memSize(monitor.getPressure(), 0) + "/s",
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
for(Consumer<Double> i : onProgress) {
|
for (Consumer<Double> i : onProgress) {
|
||||||
i.accept(percent);
|
i.accept(percent);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onChunkGenerating(int x, int z) {
|
public void onChunkGenerating(int x, int z) {
|
||||||
if(engine != null) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
draw(x, z, COLOR_GENERATING);
|
draw(x, z, COLOR_GENERATING);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onChunkGenerated(int x, int z) {
|
public void onChunkGenerated(int x, int z) {
|
||||||
if(engine != null) {
|
if (engine != null) {
|
||||||
draw(x, z, engine.draw((x << 4) + 8, (z << 4) + 8));
|
draw(x, z, engine.draw((x << 4) + 8, (z << 4) + 8));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -263,7 +251,7 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void shouldGc() {
|
private void shouldGc() {
|
||||||
if(cl.flip() && rgc > 16) {
|
if (cl.flip() && rgc > 16) {
|
||||||
System.gc();
|
System.gc();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -322,7 +310,7 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onChunkExistsInRegionGen(int x, int z) {
|
public void onChunkExistsInRegionGen(int x, int z) {
|
||||||
if(engine != null) {
|
if (engine != null) {
|
||||||
draw(x, z, engine.draw((x << 4) + 8, (z << 4) + 8));
|
draw(x, z, engine.draw((x << 4) + 8, (z << 4) + 8));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -371,10 +359,10 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
bg = (Graphics2D) image.getGraphics();
|
bg = (Graphics2D) image.getGraphics();
|
||||||
l.lock();
|
l.lock();
|
||||||
|
|
||||||
while(order.isNotEmpty()) {
|
while (order.isNotEmpty()) {
|
||||||
try {
|
try {
|
||||||
order.pop().run();
|
order.pop().run();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -388,12 +376,12 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
int h = g.getFontMetrics().getHeight() + 5;
|
int h = g.getFontMetrics().getHeight() + 5;
|
||||||
int hh = 20;
|
int hh = 20;
|
||||||
|
|
||||||
if(job.paused()) {
|
if (job.paused()) {
|
||||||
g.drawString("PAUSED", 20, hh += h);
|
g.drawString("PAUSED", 20, hh += h);
|
||||||
|
|
||||||
g.drawString("Press P to Resume", 20, hh += h);
|
g.drawString("Press P to Resume", 20, hh += h);
|
||||||
} else {
|
} else {
|
||||||
for(String i : prog) {
|
for (String i : prog) {
|
||||||
g.drawString(i, 20, hh += h);
|
g.drawString(i, 20, hh += h);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -429,7 +417,7 @@ public class PregeneratorJob implements PregenListener {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void keyReleased(KeyEvent e) {
|
public void keyReleased(KeyEvent e) {
|
||||||
if(e.getKeyCode() == KeyEvent.VK_P) {
|
if (e.getKeyCode() == KeyEvent.VK_P) {
|
||||||
PregeneratorJob.pauseResume();
|
PregeneratorJob.pauseResume();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -44,16 +44,10 @@ import org.bukkit.entity.LivingEntity;
|
|||||||
import org.bukkit.entity.Player;
|
import org.bukkit.entity.Player;
|
||||||
|
|
||||||
import javax.imageio.ImageIO;
|
import javax.imageio.ImageIO;
|
||||||
import javax.swing.JFrame;
|
import javax.swing.*;
|
||||||
import javax.swing.JPanel;
|
|
||||||
import javax.swing.event.MouseInputListener;
|
import javax.swing.event.MouseInputListener;
|
||||||
import java.awt.*;
|
import java.awt.*;
|
||||||
import java.awt.event.KeyEvent;
|
import java.awt.event.*;
|
||||||
import java.awt.event.KeyListener;
|
|
||||||
import java.awt.event.MouseEvent;
|
|
||||||
import java.awt.event.MouseMotionListener;
|
|
||||||
import java.awt.event.MouseWheelEvent;
|
|
||||||
import java.awt.event.MouseWheelListener;
|
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
@@ -143,7 +137,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
J.a(() -> {
|
J.a(() -> {
|
||||||
J.sleep(10000);
|
J.sleep(10000);
|
||||||
|
|
||||||
if(!helpIgnored && help) {
|
if (!helpIgnored && help) {
|
||||||
help = false;
|
help = false;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -167,11 +161,11 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
frame.setVisible(true);
|
frame.setVisible(true);
|
||||||
File file = Iris.getCached("Iris Icon", "https://raw.githubusercontent.com/VolmitSoftware/Iris/master/icon.png");
|
File file = Iris.getCached("Iris Icon", "https://raw.githubusercontent.com/VolmitSoftware/Iris/master/icon.png");
|
||||||
|
|
||||||
if(file != null) {
|
if (file != null) {
|
||||||
try {
|
try {
|
||||||
nv.texture = ImageIO.read(file);
|
nv.texture = ImageIO.read(file);
|
||||||
frame.setIconImage(ImageIO.read(file));
|
frame.setIconImage(ImageIO.read(file));
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -180,16 +174,16 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
public static void launch(Engine g, int i) {
|
public static void launch(Engine g, int i) {
|
||||||
J.a(() ->
|
J.a(() ->
|
||||||
createAndShowGUI(g, i, g.getWorld()));
|
createAndShowGUI(g, i, g.getWorld()));
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean updateEngine() {
|
public boolean updateEngine() {
|
||||||
if(engine.isClosed()) {
|
if (engine.isClosed()) {
|
||||||
if(world.hasRealWorld()) {
|
if (world.hasRealWorld()) {
|
||||||
try {
|
try {
|
||||||
engine = IrisToolbelt.access(world.realWorld()).getEngine();
|
engine = IrisToolbelt.access(world.realWorld()).getEngine();
|
||||||
return !engine.isClosed();
|
return !engine.isClosed();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -217,13 +211,19 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
public int getColor(double wx, double wz) {
|
public int getColor(double wx, double wz) {
|
||||||
BiFunction<Double, Double, Integer> colorFunction = (d, dx) -> Color.black.getRGB();
|
BiFunction<Double, Double, Integer> colorFunction = (d, dx) -> Color.black.getRGB();
|
||||||
|
|
||||||
switch(currentType) {
|
switch (currentType) {
|
||||||
case BIOME, DECORATOR_LOAD, OBJECT_LOAD, LAYER_LOAD -> colorFunction = (x, z) -> engine.getComplex().getTrueBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
case BIOME, DECORATOR_LOAD, OBJECT_LOAD, LAYER_LOAD ->
|
||||||
case BIOME_LAND -> colorFunction = (x, z) -> engine.getComplex().getLandBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
colorFunction = (x, z) -> engine.getComplex().getTrueBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
||||||
case BIOME_SEA -> colorFunction = (x, z) -> engine.getComplex().getSeaBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
case BIOME_LAND ->
|
||||||
case REGION -> colorFunction = (x, z) -> engine.getComplex().getRegionStream().get(x, z).getColor(engine.getComplex(), currentType).getRGB();
|
colorFunction = (x, z) -> engine.getComplex().getLandBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
||||||
case CAVE_LAND -> colorFunction = (x, z) -> engine.getComplex().getCaveBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
case BIOME_SEA ->
|
||||||
case HEIGHT -> colorFunction = (x, z) -> Color.getHSBColor(engine.getComplex().getHeightStream().get(x, z).floatValue(), 100, 100).getRGB();
|
colorFunction = (x, z) -> engine.getComplex().getSeaBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
||||||
|
case REGION ->
|
||||||
|
colorFunction = (x, z) -> engine.getComplex().getRegionStream().get(x, z).getColor(engine.getComplex(), currentType).getRGB();
|
||||||
|
case CAVE_LAND ->
|
||||||
|
colorFunction = (x, z) -> engine.getComplex().getCaveBiomeStream().get(x, z).getColor(engine, currentType).getRGB();
|
||||||
|
case HEIGHT ->
|
||||||
|
colorFunction = (x, z) -> Color.getHSBColor(engine.getComplex().getHeightStream().get(x, z).floatValue(), 100, 100).getRGB();
|
||||||
}
|
}
|
||||||
|
|
||||||
return colorFunction.apply(wx, wz);
|
return colorFunction.apply(wx, wz);
|
||||||
@@ -240,51 +240,51 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void keyPressed(KeyEvent e) {
|
public void keyPressed(KeyEvent e) {
|
||||||
if(e.getKeyCode() == KeyEvent.VK_SHIFT) {
|
if (e.getKeyCode() == KeyEvent.VK_SHIFT) {
|
||||||
shift = true;
|
shift = true;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_CONTROL) {
|
if (e.getKeyCode() == KeyEvent.VK_CONTROL) {
|
||||||
control = true;
|
control = true;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_SEMICOLON) {
|
if (e.getKeyCode() == KeyEvent.VK_SEMICOLON) {
|
||||||
debug = true;
|
debug = true;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_SLASH) {
|
if (e.getKeyCode() == KeyEvent.VK_SLASH) {
|
||||||
help = true;
|
help = true;
|
||||||
helpIgnored = true;
|
helpIgnored = true;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_ALT) {
|
if (e.getKeyCode() == KeyEvent.VK_ALT) {
|
||||||
alt = true;
|
alt = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void keyReleased(KeyEvent e) {
|
public void keyReleased(KeyEvent e) {
|
||||||
if(e.getKeyCode() == KeyEvent.VK_SEMICOLON) {
|
if (e.getKeyCode() == KeyEvent.VK_SEMICOLON) {
|
||||||
debug = false;
|
debug = false;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_SHIFT) {
|
if (e.getKeyCode() == KeyEvent.VK_SHIFT) {
|
||||||
shift = false;
|
shift = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(e.getKeyCode() == KeyEvent.VK_CONTROL) {
|
if (e.getKeyCode() == KeyEvent.VK_CONTROL) {
|
||||||
control = false;
|
control = false;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_SLASH) {
|
if (e.getKeyCode() == KeyEvent.VK_SLASH) {
|
||||||
help = false;
|
help = false;
|
||||||
helpIgnored = true;
|
helpIgnored = true;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_ALT) {
|
if (e.getKeyCode() == KeyEvent.VK_ALT) {
|
||||||
alt = false;
|
alt = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pushes
|
// Pushes
|
||||||
if(e.getKeyCode() == KeyEvent.VK_F) {
|
if (e.getKeyCode() == KeyEvent.VK_F) {
|
||||||
follow = !follow;
|
follow = !follow;
|
||||||
|
|
||||||
if(player != null && follow) {
|
if (player != null && follow) {
|
||||||
notify("Following " + player.getName() + ". Press F to disable");
|
notify("Following " + player.getName() + ". Press F to disable");
|
||||||
} else if(follow) {
|
} else if (follow) {
|
||||||
notify("Can't follow, no one is in the world");
|
notify("Can't follow, no one is in the world");
|
||||||
follow = false;
|
follow = false;
|
||||||
} else {
|
} else {
|
||||||
@@ -294,38 +294,38 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(e.getKeyCode() == KeyEvent.VK_R) {
|
if (e.getKeyCode() == KeyEvent.VK_R) {
|
||||||
dump();
|
dump();
|
||||||
notify("Refreshing Chunks");
|
notify("Refreshing Chunks");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(e.getKeyCode() == KeyEvent.VK_P) {
|
if (e.getKeyCode() == KeyEvent.VK_P) {
|
||||||
lowtile = !lowtile;
|
lowtile = !lowtile;
|
||||||
dump();
|
dump();
|
||||||
notify("Rendering " + (lowtile ? "Low" : "High") + " Quality Tiles");
|
notify("Rendering " + (lowtile ? "Low" : "High") + " Quality Tiles");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_E) {
|
if (e.getKeyCode() == KeyEvent.VK_E) {
|
||||||
eco = !eco;
|
eco = !eco;
|
||||||
dump();
|
dump();
|
||||||
notify("Using " + (eco ? "60" : "Uncapped") + " FPS Limit");
|
notify("Using " + (eco ? "60" : "Uncapped") + " FPS Limit");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_EQUALS) {
|
if (e.getKeyCode() == KeyEvent.VK_EQUALS) {
|
||||||
mscale = mscale + ((0.044 * mscale) * -3);
|
mscale = mscale + ((0.044 * mscale) * -3);
|
||||||
mscale = Math.max(mscale, 0.00001);
|
mscale = Math.max(mscale, 0.00001);
|
||||||
dump();
|
dump();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(e.getKeyCode() == KeyEvent.VK_MINUS) {
|
if (e.getKeyCode() == KeyEvent.VK_MINUS) {
|
||||||
mscale = mscale + ((0.044 * mscale) * 3);
|
mscale = mscale + ((0.044 * mscale) * 3);
|
||||||
mscale = Math.max(mscale, 0.00001);
|
mscale = Math.max(mscale, 0.00001);
|
||||||
dump();
|
dump();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(e.getKeyCode() == KeyEvent.VK_BACK_SLASH) {
|
if (e.getKeyCode() == KeyEvent.VK_BACK_SLASH) {
|
||||||
mscale = 1D;
|
mscale = 1D;
|
||||||
dump();
|
dump();
|
||||||
notify("Zoom Reset");
|
notify("Zoom Reset");
|
||||||
@@ -334,9 +334,9 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
int currentMode = currentType.ordinal();
|
int currentMode = currentType.ordinal();
|
||||||
|
|
||||||
for(RenderType i : RenderType.values()) {
|
for (RenderType i : RenderType.values()) {
|
||||||
if(e.getKeyChar() == String.valueOf(i.ordinal() + 1).charAt(0)) {
|
if (e.getKeyChar() == String.valueOf(i.ordinal() + 1).charAt(0)) {
|
||||||
if(i.ordinal() != currentMode) {
|
if (i.ordinal() != currentMode) {
|
||||||
currentType = i;
|
currentType = i;
|
||||||
dump();
|
dump();
|
||||||
notify("Rendering " + Form.capitalizeWords(currentType.name().toLowerCase().replaceAll("\\Q_\\E", " ")));
|
notify("Rendering " + Form.capitalizeWords(currentType.name().toLowerCase().replaceAll("\\Q_\\E", " ")));
|
||||||
@@ -345,7 +345,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(e.getKeyCode() == KeyEvent.VK_M) {
|
if (e.getKeyCode() == KeyEvent.VK_M) {
|
||||||
currentType = RenderType.values()[(currentMode + 1) % RenderType.values().length];
|
currentType = RenderType.values()[(currentMode + 1) % RenderType.values().length];
|
||||||
notify("Rendering " + Form.capitalizeWords(currentType.name().toLowerCase().replaceAll("\\Q_\\E", " ")));
|
notify("Rendering " + Form.capitalizeWords(currentType.name().toLowerCase().replaceAll("\\Q_\\E", " ")));
|
||||||
dump();
|
dump();
|
||||||
@@ -361,15 +361,15 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
BlockPosition key = new BlockPosition((int) mscale, Math.floorDiv(x, div), Math.floorDiv(z, div));
|
BlockPosition key = new BlockPosition((int) mscale, Math.floorDiv(x, div), Math.floorDiv(z, div));
|
||||||
fg.add(key);
|
fg.add(key);
|
||||||
|
|
||||||
if(positions.containsKey(key)) {
|
if (positions.containsKey(key)) {
|
||||||
return positions.get(key);
|
return positions.get(key);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(fastpositions.containsKey(key)) {
|
if (fastpositions.containsKey(key)) {
|
||||||
if(!working.contains(key) && working.size() < 9) {
|
if (!working.contains(key) && working.size() < 9) {
|
||||||
m.set(m.get() - 1);
|
m.set(m.get() - 1);
|
||||||
|
|
||||||
if(m.get() >= 0 && velocity < 50) {
|
if (m.get() >= 0 && velocity < 50) {
|
||||||
working.add(key);
|
working.add(key);
|
||||||
double mk = mscale;
|
double mk = mscale;
|
||||||
double mkd = scale;
|
double mkd = scale;
|
||||||
@@ -380,7 +380,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
rs.put(ps.getMilliseconds());
|
rs.put(ps.getMilliseconds());
|
||||||
working.remove(key);
|
working.remove(key);
|
||||||
|
|
||||||
if(mk == mscale && mkd == scale) {
|
if (mk == mscale && mkd == scale) {
|
||||||
positions.put(key, b);
|
positions.put(key, b);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -390,7 +390,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
return fastpositions.get(key);
|
return fastpositions.get(key);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(workingfast.contains(key) || workingfast.size() > Runtime.getRuntime().availableProcessors()) {
|
if (workingfast.contains(key) || workingfast.size() > Runtime.getRuntime().availableProcessors()) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -404,7 +404,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
rs.put(ps.getMilliseconds());
|
rs.put(ps.getMilliseconds());
|
||||||
workingfast.remove(key);
|
workingfast.remove(key);
|
||||||
|
|
||||||
if(mk == mscale && mkd == scale) {
|
if (mk == mscale && mkd == scale) {
|
||||||
fastpositions.put(key, b);
|
fastpositions.put(key, b);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -431,15 +431,11 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
@Override
|
@Override
|
||||||
public void paint(Graphics gx) {
|
public void paint(Graphics gx) {
|
||||||
|
|
||||||
if(engine.isClosed()) {
|
if (engine.isClosed()) {
|
||||||
EventQueue.invokeLater(() -> {
|
EventQueue.invokeLater(() -> {
|
||||||
try
|
try {
|
||||||
{
|
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
}
|
} catch (Throwable e) {
|
||||||
|
|
||||||
catch(Throwable e)
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -447,49 +443,49 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(updateEngine()) {
|
if (updateEngine()) {
|
||||||
dump();
|
dump();
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ox < oxp) {
|
if (ox < oxp) {
|
||||||
velocity = Math.abs(ox - oxp) * 0.36;
|
velocity = Math.abs(ox - oxp) * 0.36;
|
||||||
oxp -= velocity;
|
oxp -= velocity;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(ox > oxp) {
|
if (ox > oxp) {
|
||||||
velocity = Math.abs(oxp - ox) * 0.36;
|
velocity = Math.abs(oxp - ox) * 0.36;
|
||||||
oxp += velocity;
|
oxp += velocity;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(oz < ozp) {
|
if (oz < ozp) {
|
||||||
velocity = Math.abs(oz - ozp) * 0.36;
|
velocity = Math.abs(oz - ozp) * 0.36;
|
||||||
ozp -= velocity;
|
ozp -= velocity;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(oz > ozp) {
|
if (oz > ozp) {
|
||||||
velocity = Math.abs(ozp - oz) * 0.36;
|
velocity = Math.abs(ozp - oz) * 0.36;
|
||||||
ozp += velocity;
|
ozp += velocity;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(lx < hx) {
|
if (lx < hx) {
|
||||||
hx -= Math.abs(lx - hx) * 0.36;
|
hx -= Math.abs(lx - hx) * 0.36;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(lx > hx) {
|
if (lx > hx) {
|
||||||
hx += Math.abs(hx - lx) * 0.36;
|
hx += Math.abs(hx - lx) * 0.36;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(lz < hz) {
|
if (lz < hz) {
|
||||||
hz -= Math.abs(lz - hz) * 0.36;
|
hz -= Math.abs(lz - hz) * 0.36;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(lz > hz) {
|
if (lz > hz) {
|
||||||
hz += Math.abs(hz - lz) * 0.36;
|
hz += Math.abs(hz - lz) * 0.36;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(centities.flip()) {
|
if (centities.flip()) {
|
||||||
J.s(() -> {
|
J.s(() -> {
|
||||||
synchronized(lastEntities) {
|
synchronized (lastEntities) {
|
||||||
lastEntities.clear();
|
lastEntities.clear();
|
||||||
lastEntities.addAll(world.getEntitiesByClass(LivingEntity.class));
|
lastEntities.addAll(world.getEntitiesByClass(LivingEntity.class));
|
||||||
}
|
}
|
||||||
@@ -503,7 +499,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
double vscale = scale;
|
double vscale = scale;
|
||||||
scale = w / 12D;
|
scale = w / 12D;
|
||||||
|
|
||||||
if(scale != vscale) {
|
if (scale != vscale) {
|
||||||
positions.clear();
|
positions.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -515,15 +511,15 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
int posZ = (int) ozp;
|
int posZ = (int) ozp;
|
||||||
m.set(3);
|
m.set(3);
|
||||||
|
|
||||||
for(int r = 0; r < Math.max(w, h); r += iscale) {
|
for (int r = 0; r < Math.max(w, h); r += iscale) {
|
||||||
for(int i = -iscale; i < w + iscale; i += iscale) {
|
for (int i = -iscale; i < w + iscale; i += iscale) {
|
||||||
for(int j = -iscale; j < h + iscale; j += iscale) {
|
for (int j = -iscale; j < h + iscale; j += iscale) {
|
||||||
int a = i - (w / 2);
|
int a = i - (w / 2);
|
||||||
int b = j - (h / 2);
|
int b = j - (h / 2);
|
||||||
if(a * a + b * b <= r * r) {
|
if (a * a + b * b <= r * r) {
|
||||||
BufferedImage t = getTile(gg, iscale, Math.floorDiv((posX / iscale) + i, iscale) * iscale, Math.floorDiv((posZ / iscale) + j, iscale) * iscale, m);
|
BufferedImage t = getTile(gg, iscale, Math.floorDiv((posX / iscale) + i, iscale) * iscale, Math.floorDiv((posZ / iscale) + j, iscale) * iscale, m);
|
||||||
|
|
||||||
if(t != null) {
|
if (t != null) {
|
||||||
g.drawImage(t, i - ((posX / iscale) % (iscale)), j - ((posZ / iscale) % (iscale)), iscale, iscale, (img, infoflags, x, y, width, height) -> true);
|
g.drawImage(t, i - ((posX / iscale) % (iscale)), j - ((posZ / iscale) % (iscale)), iscale, iscale, (img, infoflags, x, y, width, height) -> true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -533,8 +529,8 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
p.end();
|
p.end();
|
||||||
|
|
||||||
for(BlockPosition i : positions.k()) {
|
for (BlockPosition i : positions.k()) {
|
||||||
if(!gg.contains(i)) {
|
if (!gg.contains(i)) {
|
||||||
positions.remove(i);
|
positions.remove(i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -542,15 +538,15 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
hanleFollow();
|
hanleFollow();
|
||||||
renderOverlays(g);
|
renderOverlays(g);
|
||||||
|
|
||||||
if(!isVisible()) {
|
if (!isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!getParent().isVisible()) {
|
if (!getParent().isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!getParent().getParent().isVisible()) {
|
if (!getParent().getParent().isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -562,7 +558,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void hanleFollow() {
|
private void hanleFollow() {
|
||||||
if(follow && player != null) {
|
if (follow && player != null) {
|
||||||
animateTo(player.getLocation().getX(), player.getLocation().getZ());
|
animateTo(player.getLocation().getX(), player.getLocation().getZ());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -570,16 +566,16 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
private void renderOverlays(Graphics2D g) {
|
private void renderOverlays(Graphics2D g) {
|
||||||
renderPlayer(g);
|
renderPlayer(g);
|
||||||
|
|
||||||
if(help) {
|
if (help) {
|
||||||
renderOverlayHelp(g);
|
renderOverlayHelp(g);
|
||||||
} else if(debug) {
|
} else if (debug) {
|
||||||
renderOverlayDebug(g);
|
renderOverlayDebug(g);
|
||||||
}
|
}
|
||||||
|
|
||||||
renderOverlayLegend(g);
|
renderOverlayLegend(g);
|
||||||
|
|
||||||
renderHoverOverlay(g, shift);
|
renderHoverOverlay(g, shift);
|
||||||
if(!notifications.isEmpty()) {
|
if (!notifications.isEmpty()) {
|
||||||
renderNotification(g);
|
renderNotification(g);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -597,8 +593,8 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
private void renderNotification(Graphics2D g) {
|
private void renderNotification(Graphics2D g) {
|
||||||
drawCardCB(g, notifications.k());
|
drawCardCB(g, notifications.k());
|
||||||
|
|
||||||
for(String i : notifications.k()) {
|
for (String i : notifications.k()) {
|
||||||
if(M.ms() > notifications.get(i)) {
|
if (M.ms() > notifications.get(i)) {
|
||||||
notifications.remove(i);
|
notifications.remove(i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -607,32 +603,32 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
private void renderPlayer(Graphics2D g) {
|
private void renderPlayer(Graphics2D g) {
|
||||||
Player b = null;
|
Player b = null;
|
||||||
|
|
||||||
for(Player i : world.getPlayers()) {
|
for (Player i : world.getPlayers()) {
|
||||||
b = i;
|
b = i;
|
||||||
renderPosition(g, i.getLocation().getX(), i.getLocation().getZ());
|
renderPosition(g, i.getLocation().getX(), i.getLocation().getZ());
|
||||||
}
|
}
|
||||||
|
|
||||||
synchronized(lastEntities) {
|
synchronized (lastEntities) {
|
||||||
double dist = Double.MAX_VALUE;
|
double dist = Double.MAX_VALUE;
|
||||||
LivingEntity h = null;
|
LivingEntity h = null;
|
||||||
|
|
||||||
for(LivingEntity i : lastEntities) {
|
for (LivingEntity i : lastEntities) {
|
||||||
if(i instanceof Player) {
|
if (i instanceof Player) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
renderMobPosition(g, i, i.getLocation().getX(), i.getLocation().getZ());
|
renderMobPosition(g, i, i.getLocation().getX(), i.getLocation().getZ());
|
||||||
if(shift) {
|
if (shift) {
|
||||||
double d = i.getLocation().distanceSquared(new Location(i.getWorld(), getWorldX(hx), i.getLocation().getY(), getWorldZ(hz)));
|
double d = i.getLocation().distanceSquared(new Location(i.getWorld(), getWorldX(hx), i.getLocation().getY(), getWorldZ(hz)));
|
||||||
|
|
||||||
if(d < dist) {
|
if (d < dist) {
|
||||||
dist = d;
|
dist = d;
|
||||||
h = i;
|
h = i;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(h != null && shift) {
|
if (h != null && shift) {
|
||||||
g.setColor(Color.red);
|
g.setColor(Color.red);
|
||||||
g.fillRoundRect((int) getScreenX(h.getLocation().getX()) - 10, (int) getScreenZ(h.getLocation().getZ()) - 10, 20, 20, 20, 20);
|
g.fillRoundRect((int) getScreenX(h.getLocation().getX()) - 10, (int) getScreenZ(h.getLocation().getZ()) - 10, 20, 20, 20, 20);
|
||||||
KList<String> k = new KList<>();
|
KList<String> k = new KList<>();
|
||||||
@@ -657,7 +653,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void renderPosition(Graphics2D g, double x, double z) {
|
private void renderPosition(Graphics2D g, double x, double z) {
|
||||||
if(texture != null) {
|
if (texture != null) {
|
||||||
g.drawImage(texture, (int) getScreenX(x), (int) getScreenZ(z), 66, 66, (img, infoflags, xx, xy, width, height) -> true);
|
g.drawImage(texture, (int) getScreenX(x), (int) getScreenZ(z), 66, 66, (img, infoflags, xx, xy, width, height) -> true);
|
||||||
} else {
|
} else {
|
||||||
g.setColor(Color.darkGray);
|
g.setColor(Color.darkGray);
|
||||||
@@ -679,7 +675,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
l.add("Biome: " + biome.getName());
|
l.add("Biome: " + biome.getName());
|
||||||
l.add("Region: " + region.getName() + "(" + region.getLoadKey() + ")");
|
l.add("Region: " + region.getName() + "(" + region.getLoadKey() + ")");
|
||||||
l.add("Block " + (int) getWorldX(hx) + ", " + (int) getWorldZ(hz));
|
l.add("Block " + (int) getWorldX(hx) + ", " + (int) getWorldZ(hz));
|
||||||
if(detailed) {
|
if (detailed) {
|
||||||
l.add("Chunk " + ((int) getWorldX(hx) >> 4) + ", " + ((int) getWorldZ(hz) >> 4));
|
l.add("Chunk " + ((int) getWorldX(hx) >> 4) + ", " + ((int) getWorldZ(hz) >> 4));
|
||||||
l.add("Region " + (((int) getWorldX(hx) >> 4) >> 5) + ", " + (((int) getWorldZ(hz) >> 4) >> 5));
|
l.add("Region " + (((int) getWorldX(hx) >> 4) >> 5) + ", " + (((int) getWorldZ(hz) >> 4) >> 5));
|
||||||
l.add("Key: " + biome.getLoadKey());
|
l.add("Key: " + biome.getLoadKey());
|
||||||
@@ -708,7 +704,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
l.add("E to toggle Eco FPS Mode");
|
l.add("E to toggle Eco FPS Mode");
|
||||||
|
|
||||||
int ff = 0;
|
int ff = 0;
|
||||||
for(RenderType i : RenderType.values()) {
|
for (RenderType i : RenderType.values()) {
|
||||||
ff++;
|
ff++;
|
||||||
l.add(ff + " to view " + Form.capitalizeWords(i.name().toLowerCase().replaceAll("\\Q_\\E", " ")));
|
l.add(ff + " to view " + Form.capitalizeWords(i.name().toLowerCase().replaceAll("\\Q_\\E", " ")));
|
||||||
}
|
}
|
||||||
@@ -738,8 +734,9 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
private void open() {
|
private void open() {
|
||||||
IrisComplex complex = engine.getComplex();
|
IrisComplex complex = engine.getComplex();
|
||||||
File r = null;
|
File r = null;
|
||||||
switch(currentType) {
|
switch (currentType) {
|
||||||
case BIOME, LAYER_LOAD, DECORATOR_LOAD, OBJECT_LOAD, HEIGHT -> r = complex.getTrueBiomeStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
case BIOME, LAYER_LOAD, DECORATOR_LOAD, OBJECT_LOAD, HEIGHT ->
|
||||||
|
r = complex.getTrueBiomeStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
||||||
case BIOME_LAND -> r = complex.getLandBiomeStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
case BIOME_LAND -> r = complex.getLandBiomeStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
||||||
case BIOME_SEA -> r = complex.getSeaBiomeStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
case BIOME_SEA -> r = complex.getSeaBiomeStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
||||||
case REGION -> r = complex.getRegionStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
case REGION -> r = complex.getRegionStream().get(getWorldX(hx), getWorldZ(hz)).openInVSCode();
|
||||||
@@ -751,7 +748,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
private void teleport() {
|
private void teleport() {
|
||||||
J.s(() -> {
|
J.s(() -> {
|
||||||
if(player != null) {
|
if (player != null) {
|
||||||
int xx = (int) getWorldX(hx);
|
int xx = (int) getWorldX(hx);
|
||||||
int zz = (int) getWorldZ(hz);
|
int zz = (int) getWorldZ(hz);
|
||||||
int h = engine.getComplex().getRoundedHeighteightStream().get(xx, zz);
|
int h = engine.getComplex().getRoundedHeighteightStream().get(xx, zz);
|
||||||
@@ -776,7 +773,7 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
int h = 0;
|
int h = 0;
|
||||||
int w = 0;
|
int w = 0;
|
||||||
|
|
||||||
for(String i : text) {
|
for (String i : text) {
|
||||||
h += g.getFontMetrics().getHeight();
|
h += g.getFontMetrics().getHeight();
|
||||||
w = Math.max(w, g.getFontMetrics().stringWidth(i));
|
w = Math.max(w, g.getFontMetrics().stringWidth(i));
|
||||||
}
|
}
|
||||||
@@ -796,14 +793,14 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
g.setColor(Color.black);
|
g.setColor(Color.black);
|
||||||
int m = 0;
|
int m = 0;
|
||||||
for(String i : text) {
|
for (String i : text) {
|
||||||
g.drawString(i, x + 14 - cw, y + 14 - ch + (++m * g.getFontMetrics().getHeight()));
|
g.drawString(i, x + 14 - cw, y + 14 - ch + (++m * g.getFontMetrics().getHeight()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void mouseWheelMoved(MouseWheelEvent e) {
|
public void mouseWheelMoved(MouseWheelEvent e) {
|
||||||
int notches = e.getWheelRotation();
|
int notches = e.getWheelRotation();
|
||||||
if(e.isControlDown()) {
|
if (e.isControlDown()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -816,9 +813,9 @@ public class VisionGUI extends JPanel implements MouseWheelListener, KeyListener
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void mouseClicked(MouseEvent e) {
|
public void mouseClicked(MouseEvent e) {
|
||||||
if(control) {
|
if (control) {
|
||||||
teleport();
|
teleport();
|
||||||
} else if(alt) {
|
} else if (alt) {
|
||||||
open();
|
open();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,13 +19,14 @@
|
|||||||
package com.volmit.iris.core.gui.components;
|
package com.volmit.iris.core.gui.components;
|
||||||
|
|
||||||
import com.volmit.iris.engine.framework.Engine;
|
import com.volmit.iris.engine.framework.Engine;
|
||||||
|
import com.volmit.iris.engine.object.IrisBiome;
|
||||||
|
import com.volmit.iris.engine.object.IrisBiomeGeneratorLink;
|
||||||
import com.volmit.iris.util.interpolation.IrisInterpolation;
|
import com.volmit.iris.util.interpolation.IrisInterpolation;
|
||||||
|
|
||||||
import java.awt.Color;
|
import java.awt.*;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
import java.util.function.BiFunction;
|
import java.util.function.BiFunction;
|
||||||
|
|
||||||
@SuppressWarnings("ClassCanBeRecord")
|
|
||||||
public class IrisRenderer {
|
public class IrisRenderer {
|
||||||
private final Engine renderer;
|
private final Engine renderer;
|
||||||
|
|
||||||
@@ -37,21 +38,43 @@ public class IrisRenderer {
|
|||||||
BufferedImage image = new BufferedImage(resolution, resolution, BufferedImage.TYPE_INT_RGB);
|
BufferedImage image = new BufferedImage(resolution, resolution, BufferedImage.TYPE_INT_RGB);
|
||||||
BiFunction<Double, Double, Integer> colorFunction = (d, dx) -> Color.black.getRGB();
|
BiFunction<Double, Double, Integer> colorFunction = (d, dx) -> Color.black.getRGB();
|
||||||
|
|
||||||
switch(currentType) {
|
switch (currentType) {
|
||||||
case BIOME, DECORATOR_LOAD, OBJECT_LOAD, LAYER_LOAD -> colorFunction = (x, z) -> renderer.getComplex().getTrueBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
case BIOME, DECORATOR_LOAD, OBJECT_LOAD, LAYER_LOAD ->
|
||||||
case BIOME_LAND -> colorFunction = (x, z) -> renderer.getComplex().getLandBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
colorFunction = (x, z) -> renderer.getComplex().getTrueBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
||||||
case BIOME_SEA -> colorFunction = (x, z) -> renderer.getComplex().getSeaBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
case BIOME_LAND ->
|
||||||
case REGION -> colorFunction = (x, z) -> renderer.getComplex().getRegionStream().get(x, z).getColor(renderer.getComplex(), currentType).getRGB();
|
colorFunction = (x, z) -> renderer.getComplex().getLandBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
||||||
case CAVE_LAND -> colorFunction = (x, z) -> renderer.getComplex().getCaveBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
case BIOME_SEA ->
|
||||||
case HEIGHT -> colorFunction = (x, z) -> Color.getHSBColor(renderer.getComplex().getHeightStream().get(x, z).floatValue(), 100, 100).getRGB();
|
colorFunction = (x, z) -> renderer.getComplex().getSeaBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
||||||
|
case REGION ->
|
||||||
|
colorFunction = (x, z) -> renderer.getComplex().getRegionStream().get(x, z).getColor(renderer.getComplex(), currentType).getRGB();
|
||||||
|
case CAVE_LAND ->
|
||||||
|
colorFunction = (x, z) -> renderer.getComplex().getCaveBiomeStream().get(x, z).getColor(renderer, currentType).getRGB();
|
||||||
|
case HEIGHT ->
|
||||||
|
colorFunction = (x, z) -> Color.getHSBColor(renderer.getComplex().getHeightStream().get(x, z).floatValue(), 100, 100).getRGB();
|
||||||
|
case CONTINENT -> colorFunction = (x, z) -> {
|
||||||
|
IrisBiome b = renderer.getBiome((int) Math.round(x), renderer.getMaxHeight() - 1, (int) Math.round(z));
|
||||||
|
IrisBiomeGeneratorLink g = b.getGenerators().get(0);
|
||||||
|
Color c;
|
||||||
|
if (g.getMax() <= 0) {
|
||||||
|
// Max is below water level, so it is most likely an ocean biome
|
||||||
|
c = Color.BLUE;
|
||||||
|
} else if (g.getMin() < 0) {
|
||||||
|
// Min is below water level, but max is not, so it is most likely a shore biome
|
||||||
|
c = Color.YELLOW;
|
||||||
|
} else {
|
||||||
|
// Both min and max are above water level, so it is most likely a land biome
|
||||||
|
c = Color.GREEN;
|
||||||
|
}
|
||||||
|
return c.getRGB();
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
double x, z;
|
double x, z;
|
||||||
int i, j;
|
int i, j;
|
||||||
for(i = 0; i < resolution; i++) {
|
for (i = 0; i < resolution; i++) {
|
||||||
x = IrisInterpolation.lerp(sx, sx + size, (double) i / (double) (resolution));
|
x = IrisInterpolation.lerp(sx, sx + size, (double) i / (double) (resolution));
|
||||||
|
|
||||||
for(j = 0; j < resolution; j++) {
|
for (j = 0; j < resolution; j++) {
|
||||||
z = IrisInterpolation.lerp(sz, sz + size, (double) j / (double) (resolution));
|
z = IrisInterpolation.lerp(sz, sz + size, (double) j / (double) (resolution));
|
||||||
image.setRGB(i, j, colorFunction.apply(x, z));
|
image.setRGB(i, j, colorFunction.apply(x, z));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,5 +19,5 @@
|
|||||||
package com.volmit.iris.core.gui.components;
|
package com.volmit.iris.core.gui.components;
|
||||||
|
|
||||||
public enum RenderType {
|
public enum RenderType {
|
||||||
BIOME, BIOME_LAND, BIOME_SEA, REGION, CAVE_LAND, HEIGHT, OBJECT_LOAD, DECORATOR_LOAD, LAYER_LOAD
|
BIOME, BIOME_LAND, BIOME_SEA, REGION, CAVE_LAND, HEIGHT, OBJECT_LOAD, DECORATOR_LOAD, CONTINENT, LAYER_LOAD
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,7 +18,7 @@
|
|||||||
|
|
||||||
package com.volmit.iris.core.gui.components;
|
package com.volmit.iris.core.gui.components;
|
||||||
|
|
||||||
import java.awt.Color;
|
import java.awt.*;
|
||||||
|
|
||||||
@FunctionalInterface
|
@FunctionalInterface
|
||||||
public interface Renderer {
|
public interface Renderer {
|
||||||
|
|||||||
@@ -0,0 +1,102 @@
|
|||||||
|
//package com.volmit.iris.core.link;
|
||||||
|
//
|
||||||
|
//import com.jojodmo.customitems.api.CustomItemsAPI;
|
||||||
|
//import com.jojodmo.customitems.item.custom.CustomItem;
|
||||||
|
//import com.jojodmo.customitems.item.custom.block.CustomMushroomBlock;
|
||||||
|
//import com.jojodmo.customitems.version.SafeMaterial;
|
||||||
|
//import com.volmit.iris.util.collection.KList;
|
||||||
|
//import com.volmit.iris.util.reflect.WrappedField;
|
||||||
|
//import com.volmit.iris.util.reflect.WrappedReturningMethod;
|
||||||
|
//import org.bukkit.block.BlockFace;
|
||||||
|
//import org.bukkit.block.data.BlockData;
|
||||||
|
//import org.bukkit.block.data.MultipleFacing;
|
||||||
|
//import org.bukkit.inventory.ItemStack;
|
||||||
|
//
|
||||||
|
//import java.util.Map;
|
||||||
|
//import java.util.MissingResourceException;
|
||||||
|
//
|
||||||
|
//public class CustomItemsDataProvider extends ExternalDataProvider {
|
||||||
|
//
|
||||||
|
// private static final String FIELD_FACES = "faces";
|
||||||
|
// private static final String METHOD_GET_MATERIAL = "getMaterial";
|
||||||
|
//
|
||||||
|
// private WrappedField<CustomMushroomBlock, Map<Integer, boolean[]>> mushroomFaces;
|
||||||
|
// private WrappedReturningMethod<CustomMushroomBlock, SafeMaterial> mushroomMaterial;
|
||||||
|
//
|
||||||
|
// public CustomItemsDataProvider() {
|
||||||
|
// super("CustomItems");
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Override
|
||||||
|
// public void init() {
|
||||||
|
// this.mushroomFaces = new WrappedField<>(CustomMushroomBlock.class, FIELD_FACES);
|
||||||
|
// this.mushroomMaterial = new WrappedReturningMethod<>(CustomMushroomBlock.class, METHOD_GET_MATERIAL);
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Override
|
||||||
|
// public BlockData getBlockData(Identifier blockId) throws MissingResourceException {
|
||||||
|
// CustomItem item = CustomItem.get(blockId.key());
|
||||||
|
// if(item == null) {
|
||||||
|
// throw new MissingResourceException("Failed to find BlockData!", blockId.namespace(), blockId.key());
|
||||||
|
// } else if(item.getBlockTexture().isSpawner()) {
|
||||||
|
// throw new MissingResourceException("Iris does not yet support SpawnerBlocks from CustomItems.", blockId.namespace(), blockId.key());
|
||||||
|
// } else if(item.getBlockTexture() != null && item.getBlockTexture().isValid()) {
|
||||||
|
// throw new MissingResourceException("Tried to fetch BlockData for a CustomItem that is not placeable!", blockId.namespace(), blockId.key());
|
||||||
|
// }
|
||||||
|
// return getMushroomData(item);
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Override
|
||||||
|
// public ItemStack getItemStack(Identifier itemId) throws MissingResourceException {
|
||||||
|
// ItemStack stack = CustomItemsAPI.getCustomItem(itemId.key());
|
||||||
|
// if(stack == null) {
|
||||||
|
// throw new MissingResourceException("Failed to find ItemData!", itemId.namespace(), itemId.key());
|
||||||
|
// }
|
||||||
|
// return stack;
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Override
|
||||||
|
// public Identifier[] getBlockTypes() {
|
||||||
|
// KList<Identifier> names = new KList<>();
|
||||||
|
// for (String name : CustomItemsAPI.listBlockCustomItemIDs()) {
|
||||||
|
// try {
|
||||||
|
// Identifier key = new Identifier("cui", name);
|
||||||
|
// if (getItemStack(key) != null)
|
||||||
|
// names.add(key);
|
||||||
|
// } catch (MissingResourceException ignored) { }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// return names.toArray(new Identifier[0]);
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Override
|
||||||
|
// public Identifier[] getItemTypes() {
|
||||||
|
// KList<Identifier> names = new KList<>();
|
||||||
|
// for (String name : CustomItemsAPI.listCustomItemIDs()) {
|
||||||
|
// try {
|
||||||
|
// Identifier key = new Identifier("cui", name);
|
||||||
|
// if (getItemStack(key) != null)
|
||||||
|
// names.add(key);
|
||||||
|
// } catch (MissingResourceException ignored) { }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// return names.toArray(new Identifier[0]);
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// @Override
|
||||||
|
// public boolean isValidProvider(Identifier key, boolean isItem) {
|
||||||
|
// return key.namespace().equalsIgnoreCase("cui");
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// private BlockData getMushroomData(CustomItem item) {
|
||||||
|
// MultipleFacing data = (MultipleFacing)mushroomMaterial.invoke(item.getBlockTexture().getMushroomId()).parseMaterial().createBlockData();
|
||||||
|
// boolean[] values = mushroomFaces.get().get(item.getBlockTexture().getMushroomId());
|
||||||
|
// data.setFace(BlockFace.DOWN, values[0]);
|
||||||
|
// data.setFace(BlockFace.EAST, values[1]);
|
||||||
|
// data.setFace(BlockFace.NORTH, values[2]);
|
||||||
|
// data.setFace(BlockFace.SOUTH, values[3]);
|
||||||
|
// data.setFace(BlockFace.UP, values[4]);
|
||||||
|
// data.setFace(BlockFace.WEST, values[5]);
|
||||||
|
// return data;
|
||||||
|
// }
|
||||||
|
//}
|
||||||
@@ -3,7 +3,6 @@ package com.volmit.iris.core.link;
|
|||||||
import lombok.Getter;
|
import lombok.Getter;
|
||||||
import lombok.RequiredArgsConstructor;
|
import lombok.RequiredArgsConstructor;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
import org.bukkit.NamespacedKey;
|
|
||||||
import org.bukkit.block.data.BlockData;
|
import org.bukkit.block.data.BlockData;
|
||||||
import org.bukkit.inventory.ItemStack;
|
import org.bukkit.inventory.ItemStack;
|
||||||
import org.bukkit.plugin.Plugin;
|
import org.bukkit.plugin.Plugin;
|
||||||
@@ -20,17 +19,19 @@ public abstract class ExternalDataProvider {
|
|||||||
return Bukkit.getPluginManager().getPlugin(pluginId);
|
return Bukkit.getPluginManager().getPlugin(pluginId);
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isPresent() {
|
public boolean isReady() {
|
||||||
return getPlugin() != null;
|
return getPlugin() != null && getPlugin().isEnabled();
|
||||||
}
|
}
|
||||||
|
|
||||||
public abstract void init();
|
public abstract void init();
|
||||||
|
|
||||||
public abstract BlockData getBlockData(NamespacedKey blockId) throws MissingResourceException;
|
public abstract BlockData getBlockData(Identifier blockId) throws MissingResourceException;
|
||||||
|
|
||||||
public abstract ItemStack getItemStack(NamespacedKey itemId) throws MissingResourceException;
|
public abstract ItemStack getItemStack(Identifier itemId) throws MissingResourceException;
|
||||||
|
|
||||||
public abstract NamespacedKey[] getBlockTypes();
|
public abstract Identifier[] getBlockTypes();
|
||||||
|
|
||||||
public abstract boolean isValidProvider(NamespacedKey namespace);
|
public abstract Identifier[] getItemTypes();
|
||||||
|
|
||||||
|
public abstract boolean isValidProvider(Identifier id, boolean isItem);
|
||||||
}
|
}
|
||||||
|
|||||||
33
src/main/java/com/volmit/iris/core/link/Identifier.java
Normal file
33
src/main/java/com/volmit/iris/core/link/Identifier.java
Normal file
@@ -0,0 +1,33 @@
|
|||||||
|
package com.volmit.iris.core.link;
|
||||||
|
|
||||||
|
import org.bukkit.NamespacedKey;
|
||||||
|
|
||||||
|
public record Identifier(String namespace, String key) {
|
||||||
|
|
||||||
|
private static final String DEFAULT_NAMESPACE = "minecraft";
|
||||||
|
|
||||||
|
public static Identifier fromString(String id) {
|
||||||
|
String[] strings = id.split(":", 2);
|
||||||
|
if (strings.length == 1) {
|
||||||
|
return new Identifier(DEFAULT_NAMESPACE, strings[0]);
|
||||||
|
} else {
|
||||||
|
return new Identifier(strings[0], strings[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return namespace + ":" + key;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object obj) {
|
||||||
|
if (obj instanceof Identifier i) {
|
||||||
|
return i.namespace().equals(this.namespace) && i.key().equals(this.key);
|
||||||
|
} else if (obj instanceof NamespacedKey i) {
|
||||||
|
return i.getNamespace().equals(this.namespace) && i.getKey().equals(this.key);
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -20,25 +20,27 @@ package com.volmit.iris.core.link;
|
|||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.tools.IrisToolbelt;
|
import com.volmit.iris.core.tools.IrisToolbelt;
|
||||||
|
import com.volmit.iris.engine.object.IrisBiome;
|
||||||
import com.volmit.iris.engine.platform.PlatformChunkGenerator;
|
import com.volmit.iris.engine.platform.PlatformChunkGenerator;
|
||||||
import me.clip.placeholderapi.expansion.PlaceholderExpansion;
|
import me.clip.placeholderapi.expansion.PlaceholderExpansion;
|
||||||
import org.bukkit.Location;
|
import org.bukkit.Location;
|
||||||
import org.bukkit.OfflinePlayer;
|
import org.bukkit.OfflinePlayer;
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
// See/update https://app.gitbook.com/@volmitsoftware/s/iris/compatability/papi/
|
// See/update https://app.gitbook.com/@volmitsoftware/s/iris/compatability/papi/
|
||||||
public class IrisPapiExpansion extends PlaceholderExpansion {
|
public class IrisPapiExpansion extends PlaceholderExpansion {
|
||||||
@Override
|
@Override
|
||||||
public String getIdentifier() {
|
public @NotNull String getIdentifier() {
|
||||||
return "iris";
|
return "iris";
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getAuthor() {
|
public @NotNull String getAuthor() {
|
||||||
return "Volmit Software";
|
return "Volmit Software";
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getVersion() {
|
public @NotNull String getVersion() {
|
||||||
return Iris.instance.getDescription().getVersion();
|
return Iris.instance.getDescription().getVersion();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -52,59 +54,63 @@ public class IrisPapiExpansion extends PlaceholderExpansion {
|
|||||||
Location l = null;
|
Location l = null;
|
||||||
PlatformChunkGenerator a = null;
|
PlatformChunkGenerator a = null;
|
||||||
|
|
||||||
if(player.isOnline()) {
|
if (player.isOnline() && player.getPlayer() != null) {
|
||||||
l = player.getPlayer().getLocation();
|
l = player.getPlayer().getLocation().add(0, 2, 0);
|
||||||
a = IrisToolbelt.access(l.getWorld());
|
a = IrisToolbelt.access(l.getWorld());
|
||||||
}
|
}
|
||||||
|
|
||||||
if(p.equalsIgnoreCase("biome_name")) {
|
if (p.equalsIgnoreCase("biome_name")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getBiome(l).getName();
|
return getBiome(a, l).getName();
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("biome_id")) {
|
} else if (p.equalsIgnoreCase("biome_id")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getBiome(l).getLoadKey();
|
return getBiome(a, l).getLoadKey();
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("biome_file")) {
|
} else if (p.equalsIgnoreCase("biome_file")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getBiome(l).getLoadFile().getPath();
|
return getBiome(a, l).getLoadFile().getPath();
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("region_name")) {
|
} else if (p.equalsIgnoreCase("region_name")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getRegion(l).getName();
|
return a.getEngine().getRegion(l).getName();
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("region_id")) {
|
} else if (p.equalsIgnoreCase("region_id")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getRegion(l).getLoadKey();
|
return a.getEngine().getRegion(l).getLoadKey();
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("region_file")) {
|
} else if (p.equalsIgnoreCase("region_file")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getRegion(l).getLoadFile().getPath();
|
return a.getEngine().getRegion(l).getLoadFile().getPath();
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("terrain_slope")) {
|
} else if (p.equalsIgnoreCase("terrain_slope")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return (a.getEngine())
|
return (a.getEngine())
|
||||||
.getComplex().getSlopeStream()
|
.getComplex().getSlopeStream()
|
||||||
.get(l.getX(), l.getZ()) + "";
|
.get(l.getX(), l.getZ()) + "";
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("terrain_height")) {
|
} else if (p.equalsIgnoreCase("terrain_height")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return Math.round(a.getEngine().getHeight(l.getBlockX(), l.getBlockZ())) + "";
|
return Math.round(a.getEngine().getHeight(l.getBlockX(), l.getBlockZ())) + "";
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("world_mode")) {
|
} else if (p.equalsIgnoreCase("world_mode")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.isStudio() ? "Studio" : "Production";
|
return a.isStudio() ? "Studio" : "Production";
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("world_seed")) {
|
} else if (p.equalsIgnoreCase("world_seed")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getSeedManager().getSeed() + "";
|
return a.getEngine().getSeedManager().getSeed() + "";
|
||||||
}
|
}
|
||||||
} else if(p.equalsIgnoreCase("world_speed")) {
|
} else if (p.equalsIgnoreCase("world_speed")) {
|
||||||
if(a != null) {
|
if (a != null) {
|
||||||
return a.getEngine().getGeneratedPerSecond() + "/s";
|
return a.getEngine().getGeneratedPerSecond() + "/s";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private IrisBiome getBiome(PlatformChunkGenerator a, Location l) {
|
||||||
|
return a.getEngine().getBiome(l.getBlockX(), l.getBlockY() - l.getWorld().getMinHeight(), l.getBlockZ());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,9 @@
|
|||||||
package com.volmit.iris.core.link;
|
package com.volmit.iris.core.link;
|
||||||
|
|
||||||
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.util.collection.KList;
|
import com.volmit.iris.util.collection.KList;
|
||||||
import dev.lone.itemsadder.api.CustomBlock;
|
import dev.lone.itemsadder.api.CustomBlock;
|
||||||
import dev.lone.itemsadder.api.CustomStack;
|
import dev.lone.itemsadder.api.CustomStack;
|
||||||
import dev.lone.itemsadder.api.ItemsAdder;
|
|
||||||
import org.bukkit.NamespacedKey;
|
|
||||||
import org.bukkit.block.data.BlockData;
|
import org.bukkit.block.data.BlockData;
|
||||||
import org.bukkit.inventory.ItemStack;
|
import org.bukkit.inventory.ItemStack;
|
||||||
|
|
||||||
@@ -12,40 +11,60 @@ import java.util.MissingResourceException;
|
|||||||
|
|
||||||
public class ItemAdderDataProvider extends ExternalDataProvider {
|
public class ItemAdderDataProvider extends ExternalDataProvider {
|
||||||
|
|
||||||
|
private KList<String> itemNamespaces, blockNamespaces;
|
||||||
|
|
||||||
public ItemAdderDataProvider() {
|
public ItemAdderDataProvider() {
|
||||||
super("ItemsAdder");
|
super("ItemsAdder");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() { }
|
public void init() {
|
||||||
|
this.itemNamespaces = new KList<>();
|
||||||
|
this.blockNamespaces = new KList<>();
|
||||||
|
|
||||||
|
for (Identifier i : getItemTypes()) {
|
||||||
|
itemNamespaces.addIfMissing(i.namespace());
|
||||||
|
}
|
||||||
|
for (Identifier i : getBlockTypes()) {
|
||||||
|
blockNamespaces.addIfMissing(i.namespace());
|
||||||
|
Iris.info("Found ItemAdder Block: " + i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public BlockData getBlockData(NamespacedKey blockId) throws MissingResourceException {
|
public BlockData getBlockData(Identifier blockId) throws MissingResourceException {
|
||||||
return CustomBlock.getBaseBlockData(blockId.toString());
|
return CustomBlock.getBaseBlockData(blockId.toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ItemStack getItemStack(NamespacedKey itemId) throws MissingResourceException {
|
public ItemStack getItemStack(Identifier itemId) throws MissingResourceException {
|
||||||
CustomStack stack = CustomStack.getInstance(itemId.toString());
|
CustomStack stack = CustomStack.getInstance(itemId.toString());
|
||||||
if(stack == null)
|
if (stack == null) {
|
||||||
throw new MissingResourceException("Failed to find ItemData!", itemId.getNamespace(), itemId.getKey());
|
throw new MissingResourceException("Failed to find ItemData!", itemId.namespace(), itemId.key());
|
||||||
|
}
|
||||||
return stack.getItemStack();
|
return stack.getItemStack();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public NamespacedKey[] getBlockTypes() {
|
public Identifier[] getBlockTypes() {
|
||||||
KList<NamespacedKey> keys = new KList<>();
|
KList<Identifier> keys = new KList<>();
|
||||||
for(String s : ItemsAdder.getNamespacedBlocksNamesInConfig())
|
for (String s : CustomBlock.getNamespacedIdsInRegistry()) {
|
||||||
keys.add(NamespacedKey.fromString(s));
|
keys.add(Identifier.fromString(s));
|
||||||
return keys.toArray(new NamespacedKey[0]);
|
}
|
||||||
|
return keys.toArray(new Identifier[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isValidProvider(NamespacedKey blockId) {
|
public Identifier[] getItemTypes() {
|
||||||
for(NamespacedKey k : getBlockTypes())
|
KList<Identifier> keys = new KList<>();
|
||||||
if(k.equals(blockId)) {
|
for (String s : CustomStack.getNamespacedIdsInRegistry()) {
|
||||||
return true;
|
keys.add(Identifier.fromString(s));
|
||||||
}
|
}
|
||||||
return false;
|
return keys.toArray(new Identifier[0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isValidProvider(Identifier id, boolean isItem) {
|
||||||
|
return isItem ? this.itemNamespaces.contains(id.namespace()) : this.blockNamespaces.contains(id.namespace());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ public class MultiverseCoreLink {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public boolean addWorld(String worldName, IrisDimension dim, String seed) {
|
public boolean addWorld(String worldName, IrisDimension dim, String seed) {
|
||||||
if(!isSupported()) {
|
if (!isSupported()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -47,11 +47,11 @@ public class MultiverseCoreLink {
|
|||||||
Object mvWorldManager = p.getClass().getDeclaredMethod("getMVWorldManager").invoke(p);
|
Object mvWorldManager = p.getClass().getDeclaredMethod("getMVWorldManager").invoke(p);
|
||||||
Method m = mvWorldManager.getClass().getDeclaredMethod("addWorld",
|
Method m = mvWorldManager.getClass().getDeclaredMethod("addWorld",
|
||||||
|
|
||||||
String.class, World.Environment.class, String.class, WorldType.class, Boolean.class, String.class, boolean.class);
|
String.class, World.Environment.class, String.class, WorldType.class, Boolean.class, String.class, boolean.class);
|
||||||
boolean b = (boolean) m.invoke(mvWorldManager, worldName, dim.getEnvironment(), seed, WorldType.NORMAL, false, "Iris", false);
|
boolean b = (boolean) m.invoke(mvWorldManager, worldName, dim.getEnvironment(), seed, WorldType.NORMAL, false, "Iris", false);
|
||||||
saveConfig();
|
saveConfig();
|
||||||
return b;
|
return b;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -67,7 +67,7 @@ public class MultiverseCoreLink {
|
|||||||
Field f = mvWorldManager.getClass().getDeclaredField("worldsFromTheConfig");
|
Field f = mvWorldManager.getClass().getDeclaredField("worldsFromTheConfig");
|
||||||
f.setAccessible(true);
|
f.setAccessible(true);
|
||||||
return (Map<String, ?>) f.get(mvWorldManager);
|
return (Map<String, ?>) f.get(mvWorldManager);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -76,7 +76,7 @@ public class MultiverseCoreLink {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void removeFromConfig(World world) {
|
public void removeFromConfig(World world) {
|
||||||
if(!isSupported()) {
|
if (!isSupported()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -85,7 +85,7 @@ public class MultiverseCoreLink {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void removeFromConfig(String world) {
|
public void removeFromConfig(String world) {
|
||||||
if(!isSupported()) {
|
if (!isSupported()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -98,7 +98,7 @@ public class MultiverseCoreLink {
|
|||||||
Plugin p = getMultiverse();
|
Plugin p = getMultiverse();
|
||||||
Object mvWorldManager = p.getClass().getDeclaredMethod("getMVWorldManager").invoke(p);
|
Object mvWorldManager = p.getClass().getDeclaredMethod("getMVWorldManager").invoke(p);
|
||||||
mvWorldManager.getClass().getDeclaredMethod("saveWorldsConfig").invoke(mvWorldManager);
|
mvWorldManager.getClass().getDeclaredMethod("saveWorldsConfig").invoke(mvWorldManager);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -112,7 +112,7 @@ public class MultiverseCoreLink {
|
|||||||
try {
|
try {
|
||||||
String t = worldNameTypes.get(worldName);
|
String t = worldNameTypes.get(worldName);
|
||||||
return t == null ? defaultType : t;
|
return t == null ? defaultType : t;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
return defaultType;
|
return defaultType;
|
||||||
}
|
}
|
||||||
@@ -128,11 +128,11 @@ public class MultiverseCoreLink {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public String envName(World.Environment environment) {
|
public String envName(World.Environment environment) {
|
||||||
if(environment == null) {
|
if (environment == null) {
|
||||||
return "normal";
|
return "normal";
|
||||||
}
|
}
|
||||||
|
|
||||||
return switch(environment) {
|
return switch (environment) {
|
||||||
case NORMAL -> "normal";
|
case NORMAL -> "normal";
|
||||||
case NETHER -> "nether";
|
case NETHER -> "nether";
|
||||||
case THE_END -> "end";
|
case THE_END -> "end";
|
||||||
|
|||||||
@@ -18,23 +18,17 @@
|
|||||||
|
|
||||||
package com.volmit.iris.core.link;
|
package com.volmit.iris.core.link;
|
||||||
|
|
||||||
|
import io.lumine.mythic.bukkit.MythicBukkit;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
import org.bukkit.Location;
|
import org.bukkit.Location;
|
||||||
import org.bukkit.entity.Entity;
|
import org.bukkit.entity.Entity;
|
||||||
import org.bukkit.plugin.Plugin;
|
import org.bukkit.plugin.Plugin;
|
||||||
|
|
||||||
import javax.annotation.Nullable;
|
import javax.annotation.Nullable;
|
||||||
import java.lang.reflect.InvocationTargetException;
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.function.BiFunction;
|
|
||||||
|
|
||||||
public class MythicMobsLink {
|
public class MythicMobsLink {
|
||||||
|
|
||||||
private Collection<String> mobs;
|
|
||||||
private BiFunction<String, Location, Entity> spawnMobFunction;
|
|
||||||
|
|
||||||
public MythicMobsLink() {
|
public MythicMobsLink() {
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -50,66 +44,16 @@ public class MythicMobsLink {
|
|||||||
/**
|
/**
|
||||||
* Spawn a mythic mob at this location
|
* Spawn a mythic mob at this location
|
||||||
*
|
*
|
||||||
* @param mob
|
* @param mob The mob
|
||||||
* The mob
|
* @param location The location
|
||||||
* @param location
|
|
||||||
* The location
|
|
||||||
* @return The mob, or null if it can't be spawned
|
* @return The mob, or null if it can't be spawned
|
||||||
*/
|
*/
|
||||||
public @Nullable
|
public @Nullable
|
||||||
Entity spawnMob(String mob, Location location) {
|
Entity spawnMob(String mob, Location location) {
|
||||||
if(!isEnabled()) return null;
|
return isEnabled() ? MythicBukkit.inst().getMobManager().spawnMob(mob, location).getEntity().getBukkitEntity() : null;
|
||||||
|
|
||||||
if(spawnMobFunction != null) {
|
|
||||||
return spawnMobFunction.apply(mob, location);
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
|
||||||
Class<?> mythicMobClass = Class.forName("io.lumine.mythic.bukkit.MythicBukkit");
|
|
||||||
Method getInst = mythicMobClass.getDeclaredMethod("inst");
|
|
||||||
Object inst = getInst.invoke(null);
|
|
||||||
Method getAPIHelper = mythicMobClass.getDeclaredMethod("getAPIHelper");
|
|
||||||
Object apiHelper = getAPIHelper.invoke(inst);
|
|
||||||
Method spawnMobMethod = apiHelper.getClass().getDeclaredMethod("spawnMythicMob", String.class, Location.class);
|
|
||||||
|
|
||||||
spawnMobFunction = (str, loc) -> {
|
|
||||||
try {
|
|
||||||
return (Entity) spawnMobMethod.invoke(apiHelper, str, loc);
|
|
||||||
} catch(InvocationTargetException | IllegalAccessException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
};
|
|
||||||
|
|
||||||
return spawnMobFunction.apply(mob, location);
|
|
||||||
} catch(Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public Collection<String> getMythicMobTypes() {
|
public Collection<String> getMythicMobTypes() {
|
||||||
if(mobs != null) {
|
return isEnabled() ? MythicBukkit.inst().getMobManager().getMobNames() : null;
|
||||||
return mobs;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(isEnabled()) {
|
|
||||||
|
|
||||||
try {
|
|
||||||
Class<?> mythicMobClass = Class.forName("io.lumine.xikage.mythicmobs.MythicMobs");
|
|
||||||
Method getInst = mythicMobClass.getDeclaredMethod("inst");
|
|
||||||
Object inst = getInst.invoke(null);
|
|
||||||
Method getMobManager = mythicMobClass.getDeclaredMethod("getMobManager");
|
|
||||||
Object mobManager = getMobManager.invoke(inst);
|
|
||||||
Method getMobNames = mobManager.getClass().getDeclaredMethod("getMobNames");
|
|
||||||
mobs = (Collection<String>) getMobNames.invoke(mobManager);
|
|
||||||
return mobs;
|
|
||||||
} catch(ClassNotFoundException | NoSuchMethodException | InvocationTargetException | IllegalAccessException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,22 +20,21 @@ package com.volmit.iris.core.link;
|
|||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.util.collection.KList;
|
import com.volmit.iris.util.collection.KList;
|
||||||
|
import com.volmit.iris.util.reflect.WrappedField;
|
||||||
|
import io.th0rgal.oraxen.api.OraxenItems;
|
||||||
import io.th0rgal.oraxen.items.ItemBuilder;
|
import io.th0rgal.oraxen.items.ItemBuilder;
|
||||||
import io.th0rgal.oraxen.items.OraxenItems;
|
|
||||||
import io.th0rgal.oraxen.mechanics.MechanicFactory;
|
import io.th0rgal.oraxen.mechanics.MechanicFactory;
|
||||||
import io.th0rgal.oraxen.mechanics.MechanicsManager;
|
import io.th0rgal.oraxen.mechanics.MechanicsManager;
|
||||||
import io.th0rgal.oraxen.mechanics.provided.gameplay.block.BlockMechanic;
|
import io.th0rgal.oraxen.mechanics.provided.gameplay.block.BlockMechanic;
|
||||||
import io.th0rgal.oraxen.mechanics.provided.gameplay.block.BlockMechanicFactory;
|
import io.th0rgal.oraxen.mechanics.provided.gameplay.block.BlockMechanicFactory;
|
||||||
import io.th0rgal.oraxen.mechanics.provided.gameplay.noteblock.NoteBlockMechanicFactory;
|
import io.th0rgal.oraxen.mechanics.provided.gameplay.noteblock.NoteBlockMechanicFactory;
|
||||||
import io.th0rgal.oraxen.utils.Utils;
|
import io.th0rgal.oraxen.mechanics.provided.gameplay.stringblock.StringBlockMechanicFactory;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
import org.bukkit.Material;
|
import org.bukkit.Material;
|
||||||
import org.bukkit.NamespacedKey;
|
|
||||||
import org.bukkit.block.data.BlockData;
|
import org.bukkit.block.data.BlockData;
|
||||||
import org.bukkit.block.data.MultipleFacing;
|
import org.bukkit.block.data.MultipleFacing;
|
||||||
import org.bukkit.inventory.ItemStack;
|
import org.bukkit.inventory.ItemStack;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.MissingResourceException;
|
import java.util.MissingResourceException;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
@@ -44,69 +43,92 @@ public class OraxenDataProvider extends ExternalDataProvider {
|
|||||||
|
|
||||||
private static final String FIELD_FACTORIES_MAP = "FACTORIES_BY_MECHANIC_ID";
|
private static final String FIELD_FACTORIES_MAP = "FACTORIES_BY_MECHANIC_ID";
|
||||||
|
|
||||||
private Map<String, MechanicFactory> factories;
|
private WrappedField<MechanicsManager, Map<String, MechanicFactory>> factories;
|
||||||
|
|
||||||
public OraxenDataProvider() { super("Oraxen"); }
|
public OraxenDataProvider() {
|
||||||
|
super("Oraxen");
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() {
|
public void init() {
|
||||||
try {
|
Iris.info("Setting up Oraxen Link...");
|
||||||
Field f = MechanicsManager.class.getDeclaredField(FIELD_FACTORIES_MAP);
|
this.factories = new WrappedField<>(MechanicsManager.class, FIELD_FACTORIES_MAP);
|
||||||
f.setAccessible(true);
|
if (this.factories.hasFailed()) {
|
||||||
factories = (Map<String, MechanicFactory>) f.get(null);
|
Iris.error("Failed to set up Oraxen Link: Unable to fetch MechanicFactoriesMap!");
|
||||||
} catch(NoSuchFieldException | IllegalAccessException e) {
|
|
||||||
Iris.error("Failed to set up Oraxen Link:");
|
|
||||||
Iris.error("\t" + e.getClass().getSimpleName());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public BlockData getBlockData(NamespacedKey blockId) throws MissingResourceException {
|
public BlockData getBlockData(Identifier blockId) throws MissingResourceException {
|
||||||
MechanicFactory f = getFactory(blockId);
|
MechanicFactory factory = getFactory(blockId);
|
||||||
if(f instanceof NoteBlockMechanicFactory)
|
if (factory instanceof NoteBlockMechanicFactory f)
|
||||||
return ((NoteBlockMechanicFactory)f).createNoteBlockData(blockId.getKey());
|
return f.createNoteBlockData(blockId.key());
|
||||||
else if(f instanceof BlockMechanicFactory) {
|
else if (factory instanceof BlockMechanicFactory f) {
|
||||||
MultipleFacing newBlockData = (MultipleFacing) Bukkit.createBlockData(Material.MUSHROOM_STEM);
|
MultipleFacing newBlockData = (MultipleFacing) Bukkit.createBlockData(Material.MUSHROOM_STEM);
|
||||||
Utils.setBlockFacing(newBlockData, ((BlockMechanic)f.getMechanic(blockId.getKey())).getCustomVariation());
|
BlockMechanic.setBlockFacing(newBlockData, ((BlockMechanic) f.getMechanic(blockId.key())).getCustomVariation());
|
||||||
return newBlockData;
|
return newBlockData;
|
||||||
|
} else if (factory instanceof StringBlockMechanicFactory f) {
|
||||||
|
return f.createTripwireData(blockId.key());
|
||||||
} else
|
} else
|
||||||
throw new MissingResourceException("Failed to find BlockData!", blockId.getNamespace(), blockId.getKey());
|
throw new MissingResourceException("Failed to find BlockData!", blockId.namespace(), blockId.key());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ItemStack getItemStack(NamespacedKey itemId) throws MissingResourceException {
|
public ItemStack getItemStack(Identifier itemId) throws MissingResourceException {
|
||||||
Optional<ItemBuilder> opt = OraxenItems.getOptionalItemById(itemId.getKey());
|
Optional<ItemBuilder> opt = OraxenItems.getOptionalItemById(itemId.key());
|
||||||
return opt.orElseThrow(() -> new MissingResourceException("Failed to find ItemData!", itemId.getNamespace(), itemId.getKey())).build();
|
return opt.orElseThrow(() -> new MissingResourceException("Failed to find ItemData!", itemId.namespace(), itemId.key())).build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public NamespacedKey[] getBlockTypes() {
|
public Identifier[] getBlockTypes() {
|
||||||
KList<NamespacedKey> names = new KList<>();
|
KList<Identifier> names = new KList<>();
|
||||||
for(String name : OraxenItems.getItemNames()) {
|
for (String name : OraxenItems.getItemNames()) {
|
||||||
try {
|
try {
|
||||||
NamespacedKey key = new NamespacedKey("oraxen", name);
|
Identifier key = new Identifier("oraxen", name);
|
||||||
if(getBlockData(key) != null)
|
if (getBlockData(key) != null)
|
||||||
names.add(key);
|
names.add(key);
|
||||||
} catch(MissingResourceException ignored) { }
|
} catch (MissingResourceException ignored) {
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return names.toArray(new NamespacedKey[0]);
|
return names.toArray(new Identifier[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isPresent() {
|
public Identifier[] getItemTypes() {
|
||||||
return super.isPresent() && factories != null;
|
KList<Identifier> names = new KList<>();
|
||||||
|
for (String name : OraxenItems.getItemNames()) {
|
||||||
|
try {
|
||||||
|
Identifier key = new Identifier("oraxen", name);
|
||||||
|
if (getItemStack(key) != null)
|
||||||
|
names.add(key);
|
||||||
|
} catch (MissingResourceException ignored) {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return names.toArray(new Identifier[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isValidProvider(NamespacedKey key) {
|
public boolean isReady() {
|
||||||
return key.getNamespace().equalsIgnoreCase("oraxen");
|
if (super.isReady()) {
|
||||||
|
if (factories == null) {
|
||||||
|
this.factories = new WrappedField<>(MechanicsManager.class, FIELD_FACTORIES_MAP);
|
||||||
|
}
|
||||||
|
return super.isReady() && !factories.hasFailed();
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private MechanicFactory getFactory(NamespacedKey key) throws MissingResourceException {
|
@Override
|
||||||
return factories.values().stream()
|
public boolean isValidProvider(Identifier key, boolean isItem) {
|
||||||
.filter(i -> i.getItems().contains(key.getKey()))
|
return key.namespace().equalsIgnoreCase("oraxen");
|
||||||
|
}
|
||||||
|
|
||||||
|
private MechanicFactory getFactory(Identifier key) throws MissingResourceException {
|
||||||
|
return factories.get().values().stream()
|
||||||
|
.filter(i -> i.getItems().contains(key.key()))
|
||||||
.findFirst()
|
.findFirst()
|
||||||
.orElseThrow(() -> new MissingResourceException("Failed to find BlockData!", key.getNamespace(), key.getKey()));
|
.orElseThrow(() -> new MissingResourceException("Failed to find BlockData!", key.namespace(), key.key()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,10 +5,8 @@ import org.bukkit.World;
|
|||||||
import org.bukkit.entity.Player;
|
import org.bukkit.entity.Player;
|
||||||
|
|
||||||
public class WorldEditLink {
|
public class WorldEditLink {
|
||||||
public static Cuboid getSelection(Player p)
|
public static Cuboid getSelection(Player p) {
|
||||||
{
|
try {
|
||||||
try
|
|
||||||
{
|
|
||||||
Object instance = Class.forName("com.sk89q.worldedit.WorldEdit").getDeclaredMethod("getInstance").invoke(null);
|
Object instance = Class.forName("com.sk89q.worldedit.WorldEdit").getDeclaredMethod("getInstance").invoke(null);
|
||||||
Object sessionManager = instance.getClass().getDeclaredMethod("getSessionManager").invoke(instance);
|
Object sessionManager = instance.getClass().getDeclaredMethod("getSessionManager").invoke(instance);
|
||||||
Object player = Class.forName("com.sk89q.worldedit.bukkit.BukkitAdapter").getDeclaredMethod("adapt", Player.class).invoke(null, p);
|
Object player = Class.forName("com.sk89q.worldedit.bukkit.BukkitAdapter").getDeclaredMethod("adapt", Player.class).invoke(null, p);
|
||||||
@@ -18,20 +16,16 @@ public class WorldEditLink {
|
|||||||
Object min = region.getClass().getDeclaredMethod("getMinimumPoint").invoke(region);
|
Object min = region.getClass().getDeclaredMethod("getMinimumPoint").invoke(region);
|
||||||
Object max = region.getClass().getDeclaredMethod("getMaximumPoint").invoke(region);
|
Object max = region.getClass().getDeclaredMethod("getMaximumPoint").invoke(region);
|
||||||
return new Cuboid(p.getWorld(),
|
return new Cuboid(p.getWorld(),
|
||||||
(int)min.getClass().getDeclaredMethod("getX").invoke(min),
|
(int) min.getClass().getDeclaredMethod("getX").invoke(min),
|
||||||
(int)min.getClass().getDeclaredMethod("getY").invoke(min),
|
(int) min.getClass().getDeclaredMethod("getY").invoke(min),
|
||||||
(int)min.getClass().getDeclaredMethod("getZ").invoke(min),
|
(int) min.getClass().getDeclaredMethod("getZ").invoke(min),
|
||||||
(int)min.getClass().getDeclaredMethod("getX").invoke(max),
|
(int) min.getClass().getDeclaredMethod("getX").invoke(max),
|
||||||
(int)min.getClass().getDeclaredMethod("getY").invoke(max),
|
(int) min.getClass().getDeclaredMethod("getY").invoke(max),
|
||||||
(int)min.getClass().getDeclaredMethod("getZ").invoke(max)
|
(int) min.getClass().getDeclaredMethod("getZ").invoke(max)
|
||||||
);
|
);
|
||||||
}
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
catch(Throwable e)
|
|
||||||
{
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
|||||||
import javax.imageio.ImageIO;
|
import javax.imageio.ImageIO;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
public class ImageResourceLoader extends ResourceLoader<IrisImage> {
|
public class ImageResourceLoader extends ResourceLoader<IrisImage> {
|
||||||
public ImageResourceLoader(File root, IrisData idm, String folderName, String resourceTypeName) {
|
public ImageResourceLoader(File root, IrisData idm, String folderName, String resourceTypeName) {
|
||||||
@@ -59,57 +60,73 @@ public class ImageResourceLoader extends ResourceLoader<IrisImage> {
|
|||||||
logLoad(j, img);
|
logLoad(j, img);
|
||||||
tlt.addAndGet(p.getMilliseconds());
|
tlt.addAndGet(p.getMilliseconds());
|
||||||
return img;
|
return img;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void getPNGFiles(File directory, Set<String> m) {
|
||||||
|
for (File file : directory.listFiles()) {
|
||||||
|
if (file.isFile() && file.getName().endsWith(".png")) {
|
||||||
|
m.add(file.getName().replaceAll("\\Q.png\\E", ""));
|
||||||
|
} else if (file.isDirectory()) {
|
||||||
|
getPNGFiles(file, m);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
public String[] getPossibleKeys() {
|
public String[] getPossibleKeys() {
|
||||||
if(possibleKeys != null) {
|
if (possibleKeys != null) {
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
||||||
KSet<String> m = new KSet<>();
|
KSet<String> m = new KSet<>();
|
||||||
|
|
||||||
for(File i : getFolders()) {
|
|
||||||
for(File j : i.listFiles()) {
|
for (File i : getFolders()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".png")) {
|
getPNGFiles(i, m);
|
||||||
m.add(j.getName().replaceAll("\\Q.png\\E", ""));
|
|
||||||
} else if(j.isDirectory()) {
|
|
||||||
for(File k : j.listFiles()) {
|
|
||||||
if(k.isFile() && k.getName().endsWith(".png")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.png\\E", ""));
|
|
||||||
} else if(k.isDirectory()) {
|
|
||||||
for(File l : k.listFiles()) {
|
|
||||||
if(l.isFile() && l.getName().endsWith(".png")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.png\\E", ""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// for (File i : getFolders()) {
|
||||||
|
// for (File j : i.listFiles()) {
|
||||||
|
// if (j.isFile() && j.getName().endsWith(".png")) {
|
||||||
|
// m.add(j.getName().replaceAll("\\Q.png\\E", ""));
|
||||||
|
// } else if (j.isDirectory()) {
|
||||||
|
// for (File k : j.listFiles()) {
|
||||||
|
// if (k.isFile() && k.getName().endsWith(".png")) {
|
||||||
|
// m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.png\\E", ""));
|
||||||
|
// } else if (k.isDirectory()) {
|
||||||
|
// for (File l : k.listFiles()) {
|
||||||
|
// if (l.isFile() && l.getName().endsWith(".png")) {
|
||||||
|
// m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.png\\E", ""));
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
KList<String> v = new KList<>(m);
|
KList<String> v = new KList<>(m);
|
||||||
possibleKeys = v.toArray(new String[0]);
|
possibleKeys = v.toArray(new String[0]);
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
public File findFile(String name) {
|
public File findFile(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".png") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".png") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".png");
|
File file = new File(i, name + ".png");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return file;
|
return file;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -124,16 +141,16 @@ public class ImageResourceLoader extends ResourceLoader<IrisImage> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private IrisImage loadRaw(String name) {
|
private IrisImage loadRaw(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".png") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".png") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return loadFile(j, name);
|
return loadFile(j, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".png");
|
File file = new File(i, name + ".png");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return loadFile(file, name);
|
return loadFile(file, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,12 +18,7 @@
|
|||||||
|
|
||||||
package com.volmit.iris.core.loader;
|
package com.volmit.iris.core.loader;
|
||||||
|
|
||||||
import com.google.gson.ExclusionStrategy;
|
import com.google.gson.*;
|
||||||
import com.google.gson.FieldAttributes;
|
|
||||||
import com.google.gson.Gson;
|
|
||||||
import com.google.gson.GsonBuilder;
|
|
||||||
import com.google.gson.TypeAdapter;
|
|
||||||
import com.google.gson.TypeAdapterFactory;
|
|
||||||
import com.google.gson.reflect.TypeToken;
|
import com.google.gson.reflect.TypeToken;
|
||||||
import com.google.gson.stream.JsonReader;
|
import com.google.gson.stream.JsonReader;
|
||||||
import com.google.gson.stream.JsonToken;
|
import com.google.gson.stream.JsonToken;
|
||||||
@@ -39,6 +34,8 @@ import com.volmit.iris.util.collection.KMap;
|
|||||||
import com.volmit.iris.util.context.IrisContext;
|
import com.volmit.iris.util.context.IrisContext;
|
||||||
import com.volmit.iris.util.format.C;
|
import com.volmit.iris.util.format.C;
|
||||||
import com.volmit.iris.util.math.RNG;
|
import com.volmit.iris.util.math.RNG;
|
||||||
|
import com.volmit.iris.util.parallel.BurstExecutor;
|
||||||
|
import com.volmit.iris.util.parallel.MultiBurst;
|
||||||
import com.volmit.iris.util.scheduling.ChronoLatch;
|
import com.volmit.iris.util.scheduling.ChronoLatch;
|
||||||
import com.volmit.iris.util.scheduling.J;
|
import com.volmit.iris.util.scheduling.J;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
@@ -100,8 +97,8 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
|
|
||||||
public static int cacheSize() {
|
public static int cacheSize() {
|
||||||
int m = 0;
|
int m = 0;
|
||||||
for(IrisData i : dataLoaders.values()) {
|
for (IrisData i : dataLoaders.values()) {
|
||||||
for(ResourceLoader<?> j : i.getLoaders().values()) {
|
for (ResourceLoader<?> j : i.getLoaders().values()) {
|
||||||
m += j.getLoadCache().getSize();
|
m += j.getLoadCache().getSize();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -116,6 +113,7 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
public static IrisObject loadAnyObject(String key) {
|
public static IrisObject loadAnyObject(String key) {
|
||||||
return loadAny(key, (dm) -> dm.getObjectLoader().load(key, false));
|
return loadAny(key, (dm) -> dm.getObjectLoader().load(key, false));
|
||||||
}
|
}
|
||||||
|
|
||||||
public static IrisMatterObject loadAnyMatter(String key) {
|
public static IrisMatterObject loadAnyMatter(String key) {
|
||||||
return loadAny(key, (dm) -> dm.getMatterLoader().load(key, false));
|
return loadAny(key, (dm) -> dm.getMatterLoader().load(key, false));
|
||||||
}
|
}
|
||||||
@@ -194,17 +192,17 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
|
|
||||||
public static <T extends IrisRegistrant> T loadAny(String key, Function<IrisData, T> v) {
|
public static <T extends IrisRegistrant> T loadAny(String key, Function<IrisData, T> v) {
|
||||||
try {
|
try {
|
||||||
for(File i : Objects.requireNonNull(Iris.instance.getDataFolder("packs").listFiles())) {
|
for (File i : Objects.requireNonNull(Iris.instance.getDataFolder("packs").listFiles())) {
|
||||||
if(i.isDirectory()) {
|
if (i.isDirectory()) {
|
||||||
IrisData dm = get(i);
|
IrisData dm = get(i);
|
||||||
T t = v.apply(dm);
|
T t = v.apply(dm);
|
||||||
|
|
||||||
if(t != null) {
|
if (t != null) {
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -215,9 +213,9 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
public ResourceLoader<?> getTypedLoaderFor(File f) {
|
public ResourceLoader<?> getTypedLoaderFor(File f) {
|
||||||
String[] k = f.getPath().split("\\Q" + File.separator + "\\E");
|
String[] k = f.getPath().split("\\Q" + File.separator + "\\E");
|
||||||
|
|
||||||
for(String i : k) {
|
for (String i : k) {
|
||||||
for(ResourceLoader<?> j : loaders.values()) {
|
for (ResourceLoader<?> j : loaders.values()) {
|
||||||
if(j.getFolderName().equals(i)) {
|
if (j.getFolderName().equals(i)) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -227,7 +225,7 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void cleanupEngine() {
|
public void cleanupEngine() {
|
||||||
if(engine != null && engine.isClosed()) {
|
if (engine != null && engine.isClosed()) {
|
||||||
engine = null;
|
engine = null;
|
||||||
Iris.debug("Dereferenced Data<Engine> " + getId() + " " + getDataFolder());
|
Iris.debug("Dereferenced Data<Engine> " + getId() + " " + getDataFolder());
|
||||||
}
|
}
|
||||||
@@ -238,30 +236,30 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
IrisContext ctx = IrisContext.get();
|
IrisContext ctx = IrisContext.get();
|
||||||
Engine engine = this.engine;
|
Engine engine = this.engine;
|
||||||
|
|
||||||
if(engine == null && ctx != null && ctx.getEngine() != null) {
|
if (engine == null && ctx != null && ctx.getEngine() != null) {
|
||||||
engine = ctx.getEngine();
|
engine = ctx.getEngine();
|
||||||
}
|
}
|
||||||
|
|
||||||
if(engine == null && t.getPreprocessors().isNotEmpty()) {
|
if (engine == null && t.getPreprocessors().isNotEmpty()) {
|
||||||
Iris.error("Failed to preprocess object " + t.getLoadKey() + " because there is no engine context here. (See stack below)");
|
Iris.error("Failed to preprocess object " + t.getLoadKey() + " because there is no engine context here. (See stack below)");
|
||||||
try {
|
try {
|
||||||
throw new RuntimeException();
|
throw new RuntimeException();
|
||||||
} catch(Throwable ex) {
|
} catch (Throwable ex) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(engine != null && t.getPreprocessors().isNotEmpty()) {
|
if (engine != null && t.getPreprocessors().isNotEmpty()) {
|
||||||
synchronized(this) {
|
synchronized (this) {
|
||||||
engine.getExecution().getAPI().setPreprocessorObject(t);
|
engine.getExecution().getAPI().setPreprocessorObject(t);
|
||||||
|
|
||||||
for(String i : t.getPreprocessors()) {
|
for (String i : t.getPreprocessors()) {
|
||||||
engine.getExecution().execute(i);
|
engine.getExecution().execute(i);
|
||||||
Iris.debug("Loader<" + C.GREEN + t.getTypeName() + C.LIGHT_PURPLE + "> iprocess " + C.YELLOW + t.getLoadKey() + C.LIGHT_PURPLE + " in <rainbow>" + i);
|
Iris.debug("Loader<" + C.GREEN + t.getTypeName() + C.LIGHT_PURPLE + "> iprocess " + C.YELLOW + t.getLoadKey() + C.LIGHT_PURPLE + " in <rainbow>" + i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.error("Failed to preprocess object!");
|
Iris.error("Failed to preprocess object!");
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -280,18 +278,18 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
try {
|
try {
|
||||||
IrisRegistrant rr = registrant.getConstructor().newInstance();
|
IrisRegistrant rr = registrant.getConstructor().newInstance();
|
||||||
ResourceLoader<T> r = null;
|
ResourceLoader<T> r = null;
|
||||||
if(registrant.equals(IrisObject.class)) {
|
if (registrant.equals(IrisObject.class)) {
|
||||||
r = (ResourceLoader<T>) new ObjectResourceLoader(dataFolder, this, rr.getFolderName(),
|
r = (ResourceLoader<T>) new ObjectResourceLoader(dataFolder, this, rr.getFolderName(),
|
||||||
rr.getTypeName());
|
rr.getTypeName());
|
||||||
} else if(registrant.equals(IrisMatterObject.class)) {
|
} else if (registrant.equals(IrisMatterObject.class)) {
|
||||||
r = (ResourceLoader<T>) new MatterObjectResourceLoader(dataFolder, this, rr.getFolderName(),
|
r = (ResourceLoader<T>) new MatterObjectResourceLoader(dataFolder, this, rr.getFolderName(),
|
||||||
rr.getTypeName());
|
rr.getTypeName());
|
||||||
} else if(registrant.equals(IrisScript.class)) {
|
} else if (registrant.equals(IrisScript.class)) {
|
||||||
r = (ResourceLoader<T>) new ScriptResourceLoader(dataFolder, this, rr.getFolderName(),
|
r = (ResourceLoader<T>) new ScriptResourceLoader(dataFolder, this, rr.getFolderName(),
|
||||||
rr.getTypeName());
|
rr.getTypeName());
|
||||||
} else if(registrant.equals(IrisImage.class)) {
|
} else if (registrant.equals(IrisImage.class)) {
|
||||||
r = (ResourceLoader<T>) new ImageResourceLoader(dataFolder, this, rr.getFolderName(),
|
r = (ResourceLoader<T>) new ImageResourceLoader(dataFolder, this, rr.getFolderName(),
|
||||||
rr.getTypeName());
|
rr.getTypeName());
|
||||||
} else {
|
} else {
|
||||||
J.attempt(() -> registrant.getConstructor().newInstance().registerTypeAdapters(builder));
|
J.attempt(() -> registrant.getConstructor().newInstance().registerTypeAdapters(builder));
|
||||||
r = new ResourceLoader<>(dataFolder, this, rr.getFolderName(), rr.getTypeName(), registrant);
|
r = new ResourceLoader<>(dataFolder, this, rr.getFolderName(), rr.getTypeName(), registrant);
|
||||||
@@ -300,7 +298,7 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
loaders.put(registrant, r);
|
loaders.put(registrant, r);
|
||||||
|
|
||||||
return r;
|
return r;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
Iris.error("Failed to create loader! " + registrant.getCanonicalName());
|
Iris.error("Failed to create loader! " + registrant.getCanonicalName());
|
||||||
}
|
}
|
||||||
@@ -311,11 +309,11 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
public synchronized void hotloaded() {
|
public synchronized void hotloaded() {
|
||||||
possibleSnippets = new KMap<>();
|
possibleSnippets = new KMap<>();
|
||||||
builder = new GsonBuilder()
|
builder = new GsonBuilder()
|
||||||
.addDeserializationExclusionStrategy(this)
|
.addDeserializationExclusionStrategy(this)
|
||||||
.addSerializationExclusionStrategy(this)
|
.addSerializationExclusionStrategy(this)
|
||||||
.setLenient()
|
.setLenient()
|
||||||
.registerTypeAdapterFactory(this)
|
.registerTypeAdapterFactory(this)
|
||||||
.setPrettyPrinting();
|
.setPrettyPrinting();
|
||||||
loaders.clear();
|
loaders.clear();
|
||||||
File packs = dataFolder;
|
File packs = dataFolder;
|
||||||
packs.mkdirs();
|
packs.mkdirs();
|
||||||
@@ -343,26 +341,26 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void dump() {
|
public void dump() {
|
||||||
for(ResourceLoader<?> i : loaders.values()) {
|
for (ResourceLoader<?> i : loaders.values()) {
|
||||||
i.clearCache();
|
i.clearCache();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void clearLists() {
|
public void clearLists() {
|
||||||
for(ResourceLoader<?> i : loaders.values()) {
|
for (ResourceLoader<?> i : loaders.values()) {
|
||||||
i.clearList();
|
i.clearList();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public String toLoadKey(File f) {
|
public String toLoadKey(File f) {
|
||||||
if(f.getPath().startsWith(getDataFolder().getPath())) {
|
if (f.getPath().startsWith(getDataFolder().getPath())) {
|
||||||
String[] full = f.getPath().split("\\Q" + File.separator + "\\E");
|
String[] full = f.getPath().split("\\Q" + File.separator + "\\E");
|
||||||
String[] df = getDataFolder().getPath().split("\\Q" + File.separator + "\\E");
|
String[] df = getDataFolder().getPath().split("\\Q" + File.separator + "\\E");
|
||||||
StringBuilder g = new StringBuilder();
|
StringBuilder g = new StringBuilder();
|
||||||
boolean m = true;
|
boolean m = true;
|
||||||
for(int i = 0; i < full.length; i++) {
|
for (int i = 0; i < full.length; i++) {
|
||||||
if(i >= df.length) {
|
if (i >= df.length) {
|
||||||
if(m) {
|
if (m) {
|
||||||
m = false;
|
m = false;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
@@ -371,8 +369,7 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
String ff = g.substring(1).split("\\Q.\\E")[0];
|
return g.substring(1).split("\\Q.\\E")[0];
|
||||||
return ff;
|
|
||||||
} else {
|
} else {
|
||||||
Iris.error("Forign file from loader " + f.getPath() + " (loader realm: " + getDataFolder().getPath() + ")");
|
Iris.error("Forign file from loader " + f.getPath() + " (loader realm: " + getDataFolder().getPath() + ")");
|
||||||
}
|
}
|
||||||
@@ -389,14 +386,14 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean shouldSkipClass(Class<?> c) {
|
public boolean shouldSkipClass(Class<?> c) {
|
||||||
if(c.equals(AtomicCache.class)) {
|
if (c.equals(AtomicCache.class)) {
|
||||||
return true;
|
return true;
|
||||||
} else return c.equals(ChronoLatch.class);
|
} else return c.equals(ChronoLatch.class);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> typeToken) {
|
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> typeToken) {
|
||||||
if(!typeToken.getRawType().isAnnotationPresent(Snippet.class)) {
|
if (!typeToken.getRawType().isAnnotationPresent(Snippet.class)) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -412,17 +409,17 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
public T read(JsonReader reader) throws IOException {
|
public T read(JsonReader reader) throws IOException {
|
||||||
TypeAdapter<T> adapter = gson.getDelegateAdapter(IrisData.this, typeToken);
|
TypeAdapter<T> adapter = gson.getDelegateAdapter(IrisData.this, typeToken);
|
||||||
|
|
||||||
if(reader.peek().equals(JsonToken.STRING)) {
|
if (reader.peek().equals(JsonToken.STRING)) {
|
||||||
String r = reader.nextString();
|
String r = reader.nextString();
|
||||||
|
|
||||||
if(r.startsWith("snippet/" + snippetType + "/")) {
|
if (r.startsWith("snippet/" + snippetType + "/")) {
|
||||||
File f = new File(getDataFolder(), r + ".json");
|
File f = new File(getDataFolder(), r + ".json");
|
||||||
|
|
||||||
if(f.exists()) {
|
if (f.exists()) {
|
||||||
try {
|
try {
|
||||||
JsonReader snippetReader = new JsonReader(new FileReader(f));
|
JsonReader snippetReader = new JsonReader(new FileReader(f));
|
||||||
return adapter.read(snippetReader);
|
return adapter.read(snippetReader);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.error("Couldn't read snippet " + r + " in " + reader.getPath() + " (" + e.getMessage() + ")");
|
Iris.error("Couldn't read snippet " + r + " in " + reader.getPath() + " (" + e.getMessage() + ")");
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@@ -435,11 +432,11 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
return adapter.read(reader);
|
return adapter.read(reader);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.error("Failed to read " + typeToken.getRawType().getCanonicalName() + "... faking objects a little to load the file at least.");
|
Iris.error("Failed to read " + typeToken.getRawType().getCanonicalName() + "... faking objects a little to load the file at least.");
|
||||||
try {
|
try {
|
||||||
return (T) typeToken.getRawType().getConstructor().newInstance();
|
return (T) typeToken.getRawType().getConstructor().newInstance();
|
||||||
} catch(Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -454,8 +451,8 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
|
|
||||||
File snippetFolder = new File(getDataFolder(), "snippet/" + f);
|
File snippetFolder = new File(getDataFolder(), "snippet/" + f);
|
||||||
|
|
||||||
if(snippetFolder.exists() && snippetFolder.isDirectory()) {
|
if (snippetFolder.exists() && snippetFolder.isDirectory()) {
|
||||||
for(File i : snippetFolder.listFiles()) {
|
for (File i : snippetFolder.listFiles()) {
|
||||||
l.add("snippet/" + f + "/" + i.getName().split("\\Q.\\E")[0]);
|
l.add("snippet/" + f + "/" + i.getName().split("\\Q.\\E")[0]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -467,4 +464,38 @@ public class IrisData implements ExclusionStrategy, TypeAdapterFactory {
|
|||||||
public boolean isClosed() {
|
public boolean isClosed() {
|
||||||
return closed;
|
return closed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void savePrefetch(Engine engine) {
|
||||||
|
BurstExecutor b = MultiBurst.burst.burst(loaders.size());
|
||||||
|
|
||||||
|
for (ResourceLoader<?> i : loaders.values()) {
|
||||||
|
b.queue(() -> {
|
||||||
|
try {
|
||||||
|
i.saveFirstAccess(engine);
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
b.complete();
|
||||||
|
Iris.info("Saved Prefetch Cache to speed up future world startups");
|
||||||
|
}
|
||||||
|
|
||||||
|
public void loadPrefetch(Engine engine) {
|
||||||
|
BurstExecutor b = MultiBurst.burst.burst(loaders.size());
|
||||||
|
|
||||||
|
for (ResourceLoader<?> i : loaders.values()) {
|
||||||
|
b.queue(() -> {
|
||||||
|
try {
|
||||||
|
i.loadFirstAccess(engine);
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
b.complete();
|
||||||
|
Iris.info("Loaded Prefetch Cache to reduce generation disk use.");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -29,7 +29,7 @@ import com.volmit.iris.util.json.JSONObject;
|
|||||||
import com.volmit.iris.util.plugin.VolmitSender;
|
import com.volmit.iris.util.plugin.VolmitSender;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
|
|
||||||
import java.awt.Desktop;
|
import java.awt.*;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
|
||||||
@Data
|
@Data
|
||||||
@@ -56,7 +56,7 @@ public abstract class IrisRegistrant {
|
|||||||
public File openInVSCode() {
|
public File openInVSCode() {
|
||||||
try {
|
try {
|
||||||
Desktop.getDesktop().open(getLoadFile());
|
Desktop.getDesktop().open(getLoadFile());
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -29,6 +29,8 @@ import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
|||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
|
||||||
public class MatterObjectResourceLoader extends ResourceLoader<IrisMatterObject> {
|
public class MatterObjectResourceLoader extends ResourceLoader<IrisMatterObject> {
|
||||||
|
private String[] possibleKeys;
|
||||||
|
|
||||||
public MatterObjectResourceLoader(File root, IrisData idm, String folderName, String resourceTypeName) {
|
public MatterObjectResourceLoader(File root, IrisData idm, String folderName, String resourceTypeName) {
|
||||||
super(root, idm, folderName, resourceTypeName, IrisMatterObject.class);
|
super(root, idm, folderName, resourceTypeName, IrisMatterObject.class);
|
||||||
loadCache = new KCache<>(this::loadRaw, IrisSettings.get().getPerformance().getObjectLoaderCacheSize());
|
loadCache = new KCache<>(this::loadRaw, IrisSettings.get().getPerformance().getObjectLoaderCacheSize());
|
||||||
@@ -56,39 +58,33 @@ public class MatterObjectResourceLoader extends ResourceLoader<IrisMatterObject>
|
|||||||
logLoad(j, t);
|
logLoad(j, t);
|
||||||
tlt.addAndGet(p.getMilliseconds());
|
tlt.addAndGet(p.getMilliseconds());
|
||||||
return t;
|
return t;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void findMatFiles(File dir, KSet<String> m) {
|
||||||
|
for (File file : dir.listFiles()) {
|
||||||
|
if (file.isFile() && file.getName().endsWith(".mat")) {
|
||||||
|
m.add(file.getName().replaceAll("\\Q.mat\\E", ""));
|
||||||
|
} else if (file.isDirectory()) {
|
||||||
|
findMatFiles(file, m);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public String[] getPossibleKeys() {
|
public String[] getPossibleKeys() {
|
||||||
if(possibleKeys != null) {
|
if (possibleKeys != null) {
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
||||||
KSet<String> m = new KSet<>();
|
KSet<String> m = new KSet<>();
|
||||||
|
|
||||||
for(File i : getFolders()) {
|
for (File folder : getFolders()) {
|
||||||
for(File j : i.listFiles()) {
|
findMatFiles(folder, m);
|
||||||
if(j.isFile() && j.getName().endsWith(".mat")) {
|
|
||||||
m.add(j.getName().replaceAll("\\Q.mat\\E", ""));
|
|
||||||
} else if(j.isDirectory()) {
|
|
||||||
for(File k : j.listFiles()) {
|
|
||||||
if(k.isFile() && k.getName().endsWith(".mat")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.mat\\E", ""));
|
|
||||||
} else if(k.isDirectory()) {
|
|
||||||
for(File l : k.listFiles()) {
|
|
||||||
if(l.isFile() && l.getName().endsWith(".mat")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.mat\\E", ""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
KList<String> v = new KList<>(m);
|
KList<String> v = new KList<>(m);
|
||||||
@@ -96,17 +92,51 @@ public class MatterObjectResourceLoader extends ResourceLoader<IrisMatterObject>
|
|||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// public String[] getPossibleKeys() {
|
||||||
|
// if (possibleKeys != null) {
|
||||||
|
// return possibleKeys;
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
||||||
|
// KSet<String> m = new KSet<>();
|
||||||
|
//
|
||||||
|
// for (File i : getFolders()) {
|
||||||
|
// for (File j : i.listFiles()) {
|
||||||
|
// if (j.isFile() && j.getName().endsWith(".mat")) {
|
||||||
|
// m.add(j.getName().replaceAll("\\Q.mat\\E", ""));
|
||||||
|
// } else if (j.isDirectory()) {
|
||||||
|
// for (File k : j.listFiles()) {
|
||||||
|
// if (k.isFile() && k.getName().endsWith(".mat")) {
|
||||||
|
// m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.mat\\E", ""));
|
||||||
|
// } else if (k.isDirectory()) {
|
||||||
|
// for (File l : k.listFiles()) {
|
||||||
|
// if (l.isFile() && l.getName().endsWith(".mat")) {
|
||||||
|
// m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.mat\\E", ""));
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// KList<String> v = new KList<>(m);
|
||||||
|
// possibleKeys = v.toArray(new String[0]);
|
||||||
|
// return possibleKeys;
|
||||||
|
// }
|
||||||
|
|
||||||
public File findFile(String name) {
|
public File findFile(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".mat") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".mat") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".mat");
|
File file = new File(i, name + ".mat");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return file;
|
return file;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -121,16 +151,16 @@ public class MatterObjectResourceLoader extends ResourceLoader<IrisMatterObject>
|
|||||||
}
|
}
|
||||||
|
|
||||||
private IrisMatterObject loadRaw(String name) {
|
private IrisMatterObject loadRaw(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".mat") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".mat") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return loadFile(j, name);
|
return loadFile(j, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".mat");
|
File file = new File(i, name + ".mat");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return loadFile(file, name);
|
return loadFile(file, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -57,7 +57,7 @@ public class ObjectResourceLoader extends ResourceLoader<IrisObject> {
|
|||||||
logLoad(j, t);
|
logLoad(j, t);
|
||||||
tlt.addAndGet(p.getMilliseconds());
|
tlt.addAndGet(p.getMilliseconds());
|
||||||
return t;
|
return t;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
||||||
return null;
|
return null;
|
||||||
@@ -65,49 +65,42 @@ public class ObjectResourceLoader extends ResourceLoader<IrisObject> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public String[] getPossibleKeys() {
|
public String[] getPossibleKeys() {
|
||||||
if(possibleKeys != null) {
|
if (possibleKeys != null) {
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
||||||
KSet<String> m = new KSet<>();
|
KSet<String> m = new KSet<>();
|
||||||
|
for (File i : getFolders()) {
|
||||||
for(File i : getFolders()) {
|
m.addAll(getFiles(i, ".iob", true));
|
||||||
for(File j : i.listFiles()) {
|
|
||||||
if(j.isFile() && j.getName().endsWith(".iob")) {
|
|
||||||
m.add(j.getName().replaceAll("\\Q.iob\\E", ""));
|
|
||||||
} else if(j.isDirectory()) {
|
|
||||||
for(File k : j.listFiles()) {
|
|
||||||
if(k.isFile() && k.getName().endsWith(".iob")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.iob\\E", ""));
|
|
||||||
} else if(k.isDirectory()) {
|
|
||||||
for(File l : k.listFiles()) {
|
|
||||||
if(l.isFile() && l.getName().endsWith(".iob")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.iob\\E", ""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
possibleKeys = m.toArray(new String[0]);
|
||||||
KList<String> v = new KList<>(m);
|
|
||||||
possibleKeys = v.toArray(new String[0]);
|
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private KList<String> getFiles(File dir, String ext, boolean skipDirName) {
|
||||||
|
KList<String> paths = new KList<>();
|
||||||
|
String name = skipDirName ? "" : dir.getName() + "/";
|
||||||
|
for (File f : dir.listFiles()) {
|
||||||
|
if (f.isFile() && f.getName().endsWith(ext)) {
|
||||||
|
paths.add(name + f.getName().replaceAll("\\Q" + ext + "\\E", ""));
|
||||||
|
} else if (f.isDirectory()) {
|
||||||
|
getFiles(f, ext, false).forEach(e -> paths.add(name + e));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return paths;
|
||||||
|
}
|
||||||
|
|
||||||
public File findFile(String name) {
|
public File findFile(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".iob") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".iob") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".iob");
|
File file = new File(i, name + ".iob");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return file;
|
return file;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -122,16 +115,16 @@ public class ObjectResourceLoader extends ResourceLoader<IrisObject> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private IrisObject loadRaw(String name) {
|
private IrisObject loadRaw(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".iob") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".iob") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return loadFile(j, name);
|
return loadFile(j, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".iob");
|
File file = new File(i, name + ".iob");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return loadFile(file, name);
|
return loadFile(file, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,37 +23,44 @@ import com.volmit.iris.Iris;
|
|||||||
import com.volmit.iris.core.IrisSettings;
|
import com.volmit.iris.core.IrisSettings;
|
||||||
import com.volmit.iris.core.project.SchemaBuilder;
|
import com.volmit.iris.core.project.SchemaBuilder;
|
||||||
import com.volmit.iris.core.service.PreservationSVC;
|
import com.volmit.iris.core.service.PreservationSVC;
|
||||||
|
import com.volmit.iris.engine.framework.Engine;
|
||||||
import com.volmit.iris.engine.framework.MeteredCache;
|
import com.volmit.iris.engine.framework.MeteredCache;
|
||||||
import com.volmit.iris.util.collection.KList;
|
import com.volmit.iris.util.collection.KList;
|
||||||
import com.volmit.iris.util.collection.KSet;
|
import com.volmit.iris.util.collection.KSet;
|
||||||
import com.volmit.iris.util.data.KCache;
|
import com.volmit.iris.util.data.KCache;
|
||||||
import com.volmit.iris.util.format.C;
|
import com.volmit.iris.util.format.C;
|
||||||
import com.volmit.iris.util.format.Form;
|
import com.volmit.iris.util.format.Form;
|
||||||
|
import com.volmit.iris.util.io.CustomOutputStream;
|
||||||
import com.volmit.iris.util.io.IO;
|
import com.volmit.iris.util.io.IO;
|
||||||
import com.volmit.iris.util.json.JSONArray;
|
import com.volmit.iris.util.json.JSONArray;
|
||||||
import com.volmit.iris.util.json.JSONObject;
|
import com.volmit.iris.util.json.JSONObject;
|
||||||
|
import com.volmit.iris.util.parallel.BurstExecutor;
|
||||||
|
import com.volmit.iris.util.parallel.MultiBurst;
|
||||||
import com.volmit.iris.util.scheduling.ChronoLatch;
|
import com.volmit.iris.util.scheduling.ChronoLatch;
|
||||||
import com.volmit.iris.util.scheduling.J;
|
import com.volmit.iris.util.scheduling.J;
|
||||||
import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.*;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
import java.util.concurrent.atomic.AtomicReference;
|
import java.util.concurrent.atomic.AtomicReference;
|
||||||
import java.util.function.Consumer;
|
import java.util.function.Consumer;
|
||||||
import java.util.function.Predicate;
|
import java.util.function.Predicate;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
|
import java.util.zip.GZIPInputStream;
|
||||||
|
import java.util.zip.GZIPOutputStream;
|
||||||
|
|
||||||
@Data
|
@Data
|
||||||
public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
||||||
public static final AtomicDouble tlt = new AtomicDouble(0);
|
public static final AtomicDouble tlt = new AtomicDouble(0);
|
||||||
private static final int CACHE_SIZE = 100000;
|
private static final int CACHE_SIZE = 100000;
|
||||||
|
protected final AtomicReference<KList<File>> folderCache;
|
||||||
|
protected KSet<String> firstAccess;
|
||||||
protected File root;
|
protected File root;
|
||||||
protected String folderName;
|
protected String folderName;
|
||||||
protected String resourceTypeName;
|
protected String resourceTypeName;
|
||||||
protected KCache<String, T> loadCache;
|
protected KCache<String, T> loadCache;
|
||||||
protected final AtomicReference<KList<File>> folderCache;
|
|
||||||
protected Class<? extends T> objectClass;
|
protected Class<? extends T> objectClass;
|
||||||
protected String cname;
|
protected String cname;
|
||||||
protected String[] possibleKeys = null;
|
protected String[] possibleKeys = null;
|
||||||
@@ -63,6 +70,7 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
|
|
||||||
public ResourceLoader(File root, IrisData manager, String folderName, String resourceTypeName, Class<? extends T> objectClass) {
|
public ResourceLoader(File root, IrisData manager, String folderName, String resourceTypeName, Class<? extends T> objectClass) {
|
||||||
this.manager = manager;
|
this.manager = manager;
|
||||||
|
firstAccess = new KSet<>();
|
||||||
folderCache = new AtomicReference<>();
|
folderCache = new AtomicReference<>();
|
||||||
sec = new ChronoLatch(5000);
|
sec = new ChronoLatch(5000);
|
||||||
loads = new AtomicInteger();
|
loads = new AtomicInteger();
|
||||||
@@ -81,7 +89,7 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
JSONObject o = new JSONObject();
|
JSONObject o = new JSONObject();
|
||||||
KList<String> fm = new KList<>();
|
KList<String> fm = new KList<>();
|
||||||
|
|
||||||
for(int g = 1; g < 8; g++) {
|
for (int g = 1; g < 8; g++) {
|
||||||
fm.add("/" + folderName + Form.repeat("/*", g) + ".json");
|
fm.add("/" + folderName + Form.repeat("/*", g) + ".json");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -94,16 +102,16 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public File findFile(String name) {
|
public File findFile(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".json") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".json") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".json");
|
File file = new File(i, name + ".json");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return file;
|
return file;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -116,11 +124,11 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
public void logLoad(File path, T t) {
|
public void logLoad(File path, T t) {
|
||||||
loads.getAndIncrement();
|
loads.getAndIncrement();
|
||||||
|
|
||||||
if(loads.get() == 1) {
|
if (loads.get() == 1) {
|
||||||
sec.flip();
|
sec.flip();
|
||||||
}
|
}
|
||||||
|
|
||||||
if(sec.flip()) {
|
if (sec.flip()) {
|
||||||
J.a(() -> {
|
J.a(() -> {
|
||||||
Iris.verbose("Loaded " + C.WHITE + loads.get() + " " + resourceTypeName + (loads.get() == 1 ? "" : "s") + C.GRAY + " (" + Form.f(getLoadCache().getSize()) + " " + resourceTypeName + (loadCache.getSize() == 1 ? "" : "s") + " Loaded)");
|
Iris.verbose("Loaded " + C.WHITE + loads.get() + " " + resourceTypeName + (loads.get() == 1 ? "" : "s") + C.GRAY + " (" + Form.f(getLoadCache().getSize()) + " " + resourceTypeName + (loadCache.getSize() == 1 ? "" : "s") + " Loaded)");
|
||||||
loads.set(0);
|
loads.set(0);
|
||||||
@@ -141,32 +149,32 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void matchFiles(File at, KList<File> files, Predicate<File> f) {
|
private void matchFiles(File at, KList<File> files, Predicate<File> f) {
|
||||||
if(at.isDirectory()) {
|
if (at.isDirectory()) {
|
||||||
for(File i : at.listFiles()) {
|
for (File i : at.listFiles()) {
|
||||||
matchFiles(i, files, f);
|
matchFiles(i, files, f);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if(f.test(at)) {
|
if (f.test(at)) {
|
||||||
files.add(at);
|
files.add(at);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public String[] getPossibleKeys() {
|
public String[] getPossibleKeys() {
|
||||||
if(possibleKeys != null) {
|
if (possibleKeys != null) {
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
KSet<String> m = new KSet<>();
|
KSet<String> m = new KSet<>();
|
||||||
KList<File> files = getFolders();
|
KList<File> files = getFolders();
|
||||||
|
|
||||||
if(files == null) {
|
if (files == null) {
|
||||||
possibleKeys = new String[0];
|
possibleKeys = new String[0];
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
for(File i : files) {
|
for (File i : files) {
|
||||||
for(File j : matchAllFiles(i, (f) -> f.getName().endsWith(".json"))) {
|
for (File j : matchAllFiles(i, (f) -> f.getName().endsWith(".json"))) {
|
||||||
m.add(i.toURI().relativize(j.toURI()).getPath().replaceAll("\\Q.json\\E", ""));
|
m.add(i.toURI().relativize(j.toURI()).getPath().replaceAll("\\Q.json\\E", ""));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -184,7 +192,7 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
try {
|
try {
|
||||||
PrecisionStopwatch p = PrecisionStopwatch.start();
|
PrecisionStopwatch p = PrecisionStopwatch.start();
|
||||||
T t = getManager().getGson()
|
T t = getManager().getGson()
|
||||||
.fromJson(preprocess(new JSONObject(IO.readAll(j))).toString(0), objectClass);
|
.fromJson(preprocess(new JSONObject(IO.readAll(j))).toString(0), objectClass);
|
||||||
t.setLoadKey(name);
|
t.setLoadKey(name);
|
||||||
t.setLoadFile(j);
|
t.setLoadFile(j);
|
||||||
t.setLoader(manager);
|
t.setLoader(manager);
|
||||||
@@ -192,7 +200,7 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
logLoad(j, t);
|
logLoad(j, t);
|
||||||
tlt.addAndGet(p.getMilliseconds());
|
tlt.addAndGet(p.getMilliseconds());
|
||||||
return t;
|
return t;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
failLoad(j, e);
|
failLoad(j, e);
|
||||||
return null;
|
return null;
|
||||||
@@ -210,10 +218,10 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
public KList<T> loadAll(KList<String> s) {
|
public KList<T> loadAll(KList<String> s) {
|
||||||
KList<T> m = new KList<>();
|
KList<T> m = new KList<>();
|
||||||
|
|
||||||
for(String i : s) {
|
for (String i : s) {
|
||||||
T t = load(i);
|
T t = load(i);
|
||||||
|
|
||||||
if(t != null) {
|
if (t != null) {
|
||||||
m.add(t);
|
m.add(t);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -221,13 +229,31 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
return m;
|
return m;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public KList<T> loadAllParallel(KList<String> s) {
|
||||||
|
KList<T> m = new KList<>();
|
||||||
|
BurstExecutor burst = MultiBurst.burst.burst(s.size());
|
||||||
|
|
||||||
|
for (String i : s) {
|
||||||
|
burst.queue(() -> {
|
||||||
|
T t = load(i);
|
||||||
|
|
||||||
|
if (t != null) {
|
||||||
|
m.add(t);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
burst.complete();
|
||||||
|
return m;
|
||||||
|
}
|
||||||
|
|
||||||
public KList<T> loadAll(KList<String> s, Consumer<T> postLoad) {
|
public KList<T> loadAll(KList<String> s, Consumer<T> postLoad) {
|
||||||
KList<T> m = new KList<>();
|
KList<T> m = new KList<>();
|
||||||
|
|
||||||
for(String i : s) {
|
for (String i : s) {
|
||||||
T t = load(i);
|
T t = load(i);
|
||||||
|
|
||||||
if(t != null) {
|
if (t != null) {
|
||||||
m.add(t);
|
m.add(t);
|
||||||
postLoad.accept(t);
|
postLoad.accept(t);
|
||||||
}
|
}
|
||||||
@@ -239,10 +265,10 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
public KList<T> loadAll(String[] s) {
|
public KList<T> loadAll(String[] s) {
|
||||||
KList<T> m = new KList<>();
|
KList<T> m = new KList<>();
|
||||||
|
|
||||||
for(String i : s) {
|
for (String i : s) {
|
||||||
T t = load(i);
|
T t = load(i);
|
||||||
|
|
||||||
if(t != null) {
|
if (t != null) {
|
||||||
m.add(t);
|
m.add(t);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -255,17 +281,17 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private T loadRaw(String name) {
|
private T loadRaw(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
//noinspection ConstantConditions
|
//noinspection ConstantConditions
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".json") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".json") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return loadFile(j, name);
|
return loadFile(j, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".json");
|
File file = new File(i, name + ".json");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return loadFile(file, name);
|
return loadFile(file, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -274,27 +300,67 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public T load(String name, boolean warn) {
|
public T load(String name, boolean warn) {
|
||||||
if(name == null) {
|
if (name == null) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(name.trim().isEmpty()) {
|
if (name.trim().isEmpty()) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
firstAccess.add(name);
|
||||||
return loadCache.get(name);
|
return loadCache.get(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void loadFirstAccess(Engine engine) throws IOException {
|
||||||
|
String id = "DIM" + Math.abs(engine.getSeedManager().getSeed() + engine.getDimension().getVersion() + engine.getDimension().getLoadKey().hashCode());
|
||||||
|
File file = Iris.instance.getDataFile("prefetch/" + id + "/" + Math.abs(getFolderName().hashCode()) + ".ipfch");
|
||||||
|
|
||||||
|
if (!file.exists()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
FileInputStream fin = new FileInputStream(file);
|
||||||
|
GZIPInputStream gzi = new GZIPInputStream(fin);
|
||||||
|
DataInputStream din = new DataInputStream(gzi);
|
||||||
|
int m = din.readInt();
|
||||||
|
KList<String> s = new KList<>();
|
||||||
|
|
||||||
|
for (int i = 0; i < m; i++) {
|
||||||
|
s.add(din.readUTF());
|
||||||
|
}
|
||||||
|
|
||||||
|
din.close();
|
||||||
|
file.deleteOnExit();
|
||||||
|
Iris.info("Loading " + s.size() + " prefetch " + getFolderName());
|
||||||
|
loadAllParallel(s);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void saveFirstAccess(Engine engine) throws IOException {
|
||||||
|
String id = "DIM" + Math.abs(engine.getSeedManager().getSeed() + engine.getDimension().getVersion() + engine.getDimension().getLoadKey().hashCode());
|
||||||
|
File file = Iris.instance.getDataFile("prefetch/" + id + "/" + Math.abs(getFolderName().hashCode()) + ".ipfch");
|
||||||
|
file.getParentFile().mkdirs();
|
||||||
|
FileOutputStream fos = new FileOutputStream(file);
|
||||||
|
GZIPOutputStream gzo = new CustomOutputStream(fos, 9);
|
||||||
|
DataOutputStream dos = new DataOutputStream(gzo);
|
||||||
|
dos.writeInt(firstAccess.size());
|
||||||
|
|
||||||
|
for (String i : firstAccess) {
|
||||||
|
dos.writeUTF(i);
|
||||||
|
}
|
||||||
|
|
||||||
|
dos.flush();
|
||||||
|
dos.close();
|
||||||
|
}
|
||||||
|
|
||||||
public KList<File> getFolders() {
|
public KList<File> getFolders() {
|
||||||
|
synchronized (folderCache) {
|
||||||
|
if (folderCache.get() == null) {
|
||||||
synchronized(folderCache) {
|
|
||||||
if(folderCache.get() == null) {
|
|
||||||
KList<File> fc = new KList<>();
|
KList<File> fc = new KList<>();
|
||||||
|
|
||||||
for(File i : root.listFiles()) {
|
for (File i : root.listFiles()) {
|
||||||
if(i.isDirectory()) {
|
if (i.isDirectory()) {
|
||||||
if(i.getName().equals(folderName)) {
|
if (i.getName().equals(folderName)) {
|
||||||
fc.add(i);
|
fc.add(i);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -311,9 +377,9 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
public KList<File> getFolders(String rc) {
|
public KList<File> getFolders(String rc) {
|
||||||
KList<File> folders = getFolders().copy();
|
KList<File> folders = getFolders().copy();
|
||||||
|
|
||||||
if(rc.contains(":")) {
|
if (rc.contains(":")) {
|
||||||
for(File i : folders.copy()) {
|
for (File i : folders.copy()) {
|
||||||
if(!rc.startsWith(i.getName() + ":")) {
|
if (!rc.startsWith(i.getName() + ":")) {
|
||||||
folders.remove(i);
|
folders.remove(i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -329,16 +395,16 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public File fileFor(T b) {
|
public File fileFor(T b) {
|
||||||
for(File i : getFolders()) {
|
for (File i : getFolders()) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".json") && j.getName().split("\\Q.\\E")[0].equals(b.getLoadKey())) {
|
if (j.isFile() && j.getName().endsWith(".json") && j.getName().split("\\Q.\\E")[0].equals(b.getLoadKey())) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, b.getLoadKey() + ".json");
|
File file = new File(i, b.getLoadKey() + ".json");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return file;
|
return file;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -358,8 +424,8 @@ public class ResourceLoader<T extends IrisRegistrant> implements MeteredCache {
|
|||||||
public KList<String> getPossibleKeys(String arg) {
|
public KList<String> getPossibleKeys(String arg) {
|
||||||
KList<String> f = new KList<>();
|
KList<String> f = new KList<>();
|
||||||
|
|
||||||
for(String i : getPossibleKeys()) {
|
for (String i : getPossibleKeys()) {
|
||||||
if(i.equalsIgnoreCase(arg) || i.toLowerCase(Locale.ROOT).startsWith(arg.toLowerCase(Locale.ROOT)) || i.toLowerCase(Locale.ROOT).contains(arg.toLowerCase(Locale.ROOT)) || arg.toLowerCase(Locale.ROOT).contains(i.toLowerCase(Locale.ROOT))) {
|
if (i.equalsIgnoreCase(arg) || i.toLowerCase(Locale.ROOT).startsWith(arg.toLowerCase(Locale.ROOT)) || i.toLowerCase(Locale.ROOT).contains(arg.toLowerCase(Locale.ROOT)) || arg.toLowerCase(Locale.ROOT).contains(i.toLowerCase(Locale.ROOT))) {
|
||||||
f.add(i);
|
f.add(i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,13 +21,13 @@ package com.volmit.iris.core.loader;
|
|||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.IrisSettings;
|
import com.volmit.iris.core.IrisSettings;
|
||||||
import com.volmit.iris.engine.object.IrisScript;
|
import com.volmit.iris.engine.object.IrisScript;
|
||||||
import com.volmit.iris.util.collection.KList;
|
|
||||||
import com.volmit.iris.util.collection.KSet;
|
|
||||||
import com.volmit.iris.util.data.KCache;
|
import com.volmit.iris.util.data.KCache;
|
||||||
import com.volmit.iris.util.io.IO;
|
import com.volmit.iris.util.io.IO;
|
||||||
import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
import com.volmit.iris.util.scheduling.PrecisionStopwatch;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
public class ScriptResourceLoader extends ResourceLoader<IrisScript> {
|
public class ScriptResourceLoader extends ResourceLoader<IrisScript> {
|
||||||
public ScriptResourceLoader(File root, IrisData idm, String folderName, String resourceTypeName) {
|
public ScriptResourceLoader(File root, IrisData idm, String folderName, String resourceTypeName) {
|
||||||
@@ -53,57 +53,88 @@ public class ScriptResourceLoader extends ResourceLoader<IrisScript> {
|
|||||||
logLoad(j, t);
|
logLoad(j, t);
|
||||||
tlt.addAndGet(p.getMilliseconds());
|
tlt.addAndGet(p.getMilliseconds());
|
||||||
return t;
|
return t;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
Iris.warn("Couldn't read " + resourceTypeName + " file: " + j.getPath() + ": " + e.getMessage());
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public String[] getPossibleKeys() {
|
public String[] getPossibleKeys() {
|
||||||
if(possibleKeys != null) {
|
if (possibleKeys != null) {
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
||||||
KSet<String> m = new KSet<>();
|
Set<String> keys = new HashSet<>();
|
||||||
|
|
||||||
for(File i : getFolders()) {
|
for (File i : getFolders()) {
|
||||||
for(File j : i.listFiles()) {
|
if (i.isDirectory()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".js")) {
|
keys.addAll(getKeysInDirectory(i));
|
||||||
m.add(j.getName().replaceAll("\\Q.js\\E", ""));
|
|
||||||
} else if(j.isDirectory()) {
|
|
||||||
for(File k : j.listFiles()) {
|
|
||||||
if(k.isFile() && k.getName().endsWith(".js")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.js\\E", ""));
|
|
||||||
} else if(k.isDirectory()) {
|
|
||||||
for(File l : k.listFiles()) {
|
|
||||||
if(l.isFile() && l.getName().endsWith(".js")) {
|
|
||||||
m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.js\\E", ""));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
KList<String> v = new KList<>(m);
|
possibleKeys = keys.toArray(new String[0]);
|
||||||
possibleKeys = v.toArray(new String[0]);
|
|
||||||
return possibleKeys;
|
return possibleKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Set<String> getKeysInDirectory(File directory) {
|
||||||
|
Set<String> keys = new HashSet<>();
|
||||||
|
for (File file : directory.listFiles()) {
|
||||||
|
if (file.isFile() && file.getName().endsWith(".js")) {
|
||||||
|
keys.add(file.getName().replaceAll("\\Q.js\\E", ""));
|
||||||
|
} else if (file.isDirectory()) {
|
||||||
|
keys.addAll(getKeysInDirectory(file));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return keys;
|
||||||
|
}
|
||||||
|
|
||||||
|
// public String[] getPossibleKeys() {
|
||||||
|
// if (possibleKeys != null) {
|
||||||
|
// return possibleKeys;
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// Iris.debug("Building " + resourceTypeName + " Possibility Lists");
|
||||||
|
// KSet<String> m = new KSet<>();
|
||||||
|
//
|
||||||
|
// for (File i : getFolders()) {
|
||||||
|
// for (File j : i.listFiles()) {
|
||||||
|
// if (j.isFile() && j.getName().endsWith(".js")) {
|
||||||
|
// m.add(j.getName().replaceAll("\\Q.js\\E", ""));
|
||||||
|
// } else if (j.isDirectory()) {
|
||||||
|
// for (File k : j.listFiles()) {
|
||||||
|
// if (k.isFile() && k.getName().endsWith(".js")) {
|
||||||
|
// m.add(j.getName() + "/" + k.getName().replaceAll("\\Q.js\\E", ""));
|
||||||
|
// } else if (k.isDirectory()) {
|
||||||
|
// for (File l : k.listFiles()) {
|
||||||
|
// if (l.isFile() && l.getName().endsWith(".js")) {
|
||||||
|
// m.add(j.getName() + "/" + k.getName() + "/" + l.getName().replaceAll("\\Q.js\\E", ""));
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// KList<String> v = new KList<>(m);
|
||||||
|
// possibleKeys = v.toArray(new String[0]);
|
||||||
|
// return possibleKeys;
|
||||||
|
// }
|
||||||
|
|
||||||
public File findFile(String name) {
|
public File findFile(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".js") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".js") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".js");
|
File file = new File(i, name + ".js");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return file;
|
return file;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -114,16 +145,16 @@ public class ScriptResourceLoader extends ResourceLoader<IrisScript> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private IrisScript loadRaw(String name) {
|
private IrisScript loadRaw(String name) {
|
||||||
for(File i : getFolders(name)) {
|
for (File i : getFolders(name)) {
|
||||||
for(File j : i.listFiles()) {
|
for (File j : i.listFiles()) {
|
||||||
if(j.isFile() && j.getName().endsWith(".js") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
if (j.isFile() && j.getName().endsWith(".js") && j.getName().split("\\Q.\\E")[0].equals(name)) {
|
||||||
return loadFile(j, name);
|
return loadFile(j, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
File file = new File(i, name + ".js");
|
File file = new File(i, name + ".js");
|
||||||
|
|
||||||
if(file.exists()) {
|
if (file.exists()) {
|
||||||
return loadFile(file, name);
|
return loadFile(file, name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ package com.volmit.iris.core.nms;
|
|||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.IrisSettings;
|
import com.volmit.iris.core.IrisSettings;
|
||||||
import com.volmit.iris.core.nms.v19_1.NMSBinding19_1;
|
import com.volmit.iris.core.nms.v20.NMSBinding1_20_1;
|
||||||
import com.volmit.iris.core.nms.v1X.NMSBinding1X;
|
import com.volmit.iris.core.nms.v1X.NMSBinding1X;
|
||||||
import com.volmit.iris.util.collection.KMap;
|
import com.volmit.iris.util.collection.KMap;
|
||||||
import org.bukkit.Bukkit;
|
import org.bukkit.Bukkit;
|
||||||
@@ -28,7 +28,7 @@ import org.bukkit.Bukkit;
|
|||||||
public class INMS {
|
public class INMS {
|
||||||
//@builder
|
//@builder
|
||||||
private static final KMap<String, Class<? extends INMSBinding>> bindings = new KMap<String, Class<? extends INMSBinding>>()
|
private static final KMap<String, Class<? extends INMSBinding>> bindings = new KMap<String, Class<? extends INMSBinding>>()
|
||||||
.qput("v1_19_R1", NMSBinding19_1.class);
|
.qput("v1_20_R1", NMSBinding1_20_1.class);
|
||||||
//@done
|
//@done
|
||||||
private static final INMSBinding binding = bind();
|
private static final INMSBinding binding = bind();
|
||||||
|
|
||||||
@@ -37,13 +37,13 @@ public class INMS {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static String getNMSTag() {
|
public static String getNMSTag() {
|
||||||
if(IrisSettings.get().getGeneral().isDisableNMS()) {
|
if (IrisSettings.get().getGeneral().isDisableNMS()) {
|
||||||
return "BUKKIT";
|
return "BUKKIT";
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
return Bukkit.getServer().getClass().getCanonicalName().split("\\Q.\\E")[3];
|
return Bukkit.getServer().getClass().getCanonicalName().split("\\Q.\\E")[3];
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.error("Failed to determine server nms version!");
|
Iris.error("Failed to determine server nms version!");
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
@@ -56,13 +56,13 @@ public class INMS {
|
|||||||
String code = getNMSTag();
|
String code = getNMSTag();
|
||||||
Iris.info("Locating NMS Binding for " + code);
|
Iris.info("Locating NMS Binding for " + code);
|
||||||
|
|
||||||
if(bindings.containsKey(code)) {
|
if (bindings.containsKey(code)) {
|
||||||
try {
|
try {
|
||||||
INMSBinding b = bindings.get(code).getConstructor().newInstance();
|
INMSBinding b = bindings.get(code).getConstructor().newInstance();
|
||||||
Iris.info("Craftbukkit " + code + " <-> " + b.getClass().getSimpleName() + " Successfully Bound");
|
Iris.info("Craftbukkit " + code + " <-> " + b.getClass().getSimpleName() + " Successfully Bound");
|
||||||
|
|
||||||
return b;
|
return b;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -18,9 +18,11 @@
|
|||||||
|
|
||||||
package com.volmit.iris.core.nms;
|
package com.volmit.iris.core.nms;
|
||||||
|
|
||||||
|
import com.volmit.iris.util.mantle.Mantle;
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCABiomeContainer;
|
import com.volmit.iris.util.nbt.mca.palette.MCABiomeContainer;
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAPaletteAccess;
|
import com.volmit.iris.util.nbt.mca.palette.MCAPaletteAccess;
|
||||||
import com.volmit.iris.util.nbt.tag.CompoundTag;
|
import com.volmit.iris.util.nbt.tag.CompoundTag;
|
||||||
|
import org.bukkit.Chunk;
|
||||||
import org.bukkit.Location;
|
import org.bukkit.Location;
|
||||||
import org.bukkit.World;
|
import org.bukkit.World;
|
||||||
import org.bukkit.WorldCreator;
|
import org.bukkit.WorldCreator;
|
||||||
@@ -54,8 +56,11 @@ public interface INMSBinding {
|
|||||||
String getTrueBiomeBaseKey(Location location);
|
String getTrueBiomeBaseKey(Location location);
|
||||||
|
|
||||||
Object getCustomBiomeBaseFor(String mckey);
|
Object getCustomBiomeBaseFor(String mckey);
|
||||||
|
|
||||||
Object getCustomBiomeBaseHolderFor(String mckey);
|
Object getCustomBiomeBaseHolderFor(String mckey);
|
||||||
|
|
||||||
|
int getBiomeBaseIdForKey(String key);
|
||||||
|
|
||||||
String getKeyForBiomeBase(Object biomeBase);
|
String getKeyForBiomeBase(Object biomeBase);
|
||||||
|
|
||||||
Object getBiomeBase(World world, Biome biome);
|
Object getBiomeBase(World world, Biome biome);
|
||||||
@@ -83,4 +88,6 @@ public interface INMSBinding {
|
|||||||
}
|
}
|
||||||
|
|
||||||
MCAPaletteAccess createPalette();
|
MCAPaletteAccess createPalette();
|
||||||
|
|
||||||
|
void injectBiomesFromMantle(Chunk e, Mantle mantle);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,159 +0,0 @@
|
|||||||
/*
|
|
||||||
* Iris is a World Generator for Minecraft Bukkit Servers
|
|
||||||
* Copyright (c) 2022 Arcane Arts (Volmit Software)
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU General Public License as published by
|
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
|
||||||
* (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU General Public License
|
|
||||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package com.volmit.iris.core.nms;
|
|
||||||
|
|
||||||
import com.volmit.iris.Iris;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
public enum NMSVersion {
|
|
||||||
R1_19_1,
|
|
||||||
R1_18_2,
|
|
||||||
R1_18,
|
|
||||||
R1_17,
|
|
||||||
R1_16,
|
|
||||||
R1_15,
|
|
||||||
R1_14,
|
|
||||||
R1_13,
|
|
||||||
R1_13_1,
|
|
||||||
R1_12,
|
|
||||||
R1_11,
|
|
||||||
R1_10,
|
|
||||||
R1_9_4,
|
|
||||||
R1_9_2,
|
|
||||||
R1_8;
|
|
||||||
|
|
||||||
public static NMSVersion getMinimum() {
|
|
||||||
return values()[values().length - 1];
|
|
||||||
}
|
|
||||||
|
|
||||||
public static NMSVersion getMaximum() {
|
|
||||||
return values()[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
public static NMSVersion current() {
|
|
||||||
if(tryVersion("1_8_R3")) {
|
|
||||||
return R1_8;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_9_R1")) {
|
|
||||||
return R1_9_2;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_9_R2")) {
|
|
||||||
return R1_9_4;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_10_R1")) {
|
|
||||||
return R1_10;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_11_R1")) {
|
|
||||||
return R1_11;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_12_R1")) {
|
|
||||||
return R1_12;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_13_R1")) {
|
|
||||||
return R1_13;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_13_R2")) {
|
|
||||||
return R1_13_1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_14_R1")) {
|
|
||||||
return R1_14;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_15_R1")) {
|
|
||||||
return R1_15;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_16_R1")) {
|
|
||||||
return R1_16;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_17_R1")) {
|
|
||||||
return R1_17;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(tryVersion("1_18_R1")) {
|
|
||||||
return R1_18;
|
|
||||||
}
|
|
||||||
if(tryVersion("1_18_R2")) {
|
|
||||||
return R1_18_2;
|
|
||||||
}
|
|
||||||
if(tryVersion("1_19_R1")) {
|
|
||||||
return R1_19_1;
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static boolean tryVersion(String v) {
|
|
||||||
try {
|
|
||||||
Class.forName("org.bukkit.craftbukkit.v" + v + ".CraftWorld");
|
|
||||||
return true;
|
|
||||||
} catch(Throwable e) {
|
|
||||||
Iris.reportError(e);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<NMSVersion> getAboveInclusive() {
|
|
||||||
List<NMSVersion> n = new ArrayList<>();
|
|
||||||
|
|
||||||
for(NMSVersion i : values()) {
|
|
||||||
if(i.ordinal() >= ordinal()) {
|
|
||||||
n.add(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return n;
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<NMSVersion> betweenInclusive(NMSVersion other) {
|
|
||||||
List<NMSVersion> n = new ArrayList<>();
|
|
||||||
|
|
||||||
for(NMSVersion i : values()) {
|
|
||||||
if(i.ordinal() <= Math.max(other.ordinal(), ordinal()) && i.ordinal() >= Math.min(ordinal(), other.ordinal())) {
|
|
||||||
n.add(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return n;
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<NMSVersion> getBelowInclusive() {
|
|
||||||
List<NMSVersion> n = new ArrayList<>();
|
|
||||||
|
|
||||||
for(NMSVersion i : values()) {
|
|
||||||
if(i.ordinal() <= ordinal()) {
|
|
||||||
n.add(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return n;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -20,9 +20,11 @@ package com.volmit.iris.core.nms.v1X;
|
|||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.nms.INMSBinding;
|
import com.volmit.iris.core.nms.INMSBinding;
|
||||||
|
import com.volmit.iris.util.mantle.Mantle;
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCABiomeContainer;
|
import com.volmit.iris.util.nbt.mca.palette.MCABiomeContainer;
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAPaletteAccess;
|
import com.volmit.iris.util.nbt.mca.palette.MCAPaletteAccess;
|
||||||
import com.volmit.iris.util.nbt.tag.CompoundTag;
|
import com.volmit.iris.util.nbt.tag.CompoundTag;
|
||||||
|
import org.bukkit.Chunk;
|
||||||
import org.bukkit.Location;
|
import org.bukkit.Location;
|
||||||
import org.bukkit.World;
|
import org.bukkit.World;
|
||||||
import org.bukkit.block.Biome;
|
import org.bukkit.block.Biome;
|
||||||
@@ -35,12 +37,12 @@ public class NMSBinding1X implements INMSBinding {
|
|||||||
@SuppressWarnings("ConstantConditions")
|
@SuppressWarnings("ConstantConditions")
|
||||||
private static boolean testCustomHeight() {
|
private static boolean testCustomHeight() {
|
||||||
try {
|
try {
|
||||||
if(World.class.getDeclaredMethod("getMaxHeight") != null && World.class.getDeclaredMethod("getMinHeight") != null)
|
if (World.class.getDeclaredMethod("getMaxHeight") != null && World.class.getDeclaredMethod("getMinHeight") != null)
|
||||||
;
|
;
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
} catch(Throwable ignored) {
|
} catch (Throwable ignored) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -57,6 +59,11 @@ public class NMSBinding1X implements INMSBinding {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void injectBiomesFromMantle(Chunk e, Mantle mantle) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void deserializeTile(CompoundTag s, Location newPosition) {
|
public void deserializeTile(CompoundTag s, Location newPosition) {
|
||||||
|
|
||||||
@@ -117,6 +124,11 @@ public class NMSBinding1X implements INMSBinding {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getBiomeBaseIdForKey(String key) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getKeyForBiomeBase(Object biomeBase) {
|
public String getKeyForBiomeBase(Object biomeBase) {
|
||||||
return null;
|
return null;
|
||||||
|
|||||||
@@ -0,0 +1,169 @@
|
|||||||
|
package com.volmit.iris.core.nms.v20;
|
||||||
|
|
||||||
|
import com.mojang.serialization.Codec;
|
||||||
|
import com.volmit.iris.Iris;
|
||||||
|
import com.volmit.iris.engine.data.cache.AtomicCache;
|
||||||
|
import com.volmit.iris.engine.framework.Engine;
|
||||||
|
import com.volmit.iris.engine.object.IrisBiome;
|
||||||
|
import com.volmit.iris.engine.object.IrisBiomeCustom;
|
||||||
|
import com.volmit.iris.util.collection.KMap;
|
||||||
|
import com.volmit.iris.util.math.RNG;
|
||||||
|
import net.minecraft.core.Holder;
|
||||||
|
import net.minecraft.core.Registry;
|
||||||
|
import net.minecraft.core.RegistryAccess;
|
||||||
|
import net.minecraft.core.registries.Registries;
|
||||||
|
import net.minecraft.resources.ResourceKey;
|
||||||
|
import net.minecraft.resources.ResourceLocation;
|
||||||
|
import net.minecraft.world.level.biome.Biome;
|
||||||
|
import net.minecraft.world.level.biome.BiomeSource;
|
||||||
|
import net.minecraft.world.level.biome.Climate;
|
||||||
|
import org.bukkit.Bukkit;
|
||||||
|
import org.bukkit.World;
|
||||||
|
import org.bukkit.craftbukkit.v1_20_R1.CraftServer;
|
||||||
|
import org.bukkit.craftbukkit.v1_20_R1.CraftWorld;
|
||||||
|
import org.bukkit.craftbukkit.v1_20_R1.block.CraftBlock;
|
||||||
|
import java.lang.reflect.Field;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.stream.Stream;
|
||||||
|
|
||||||
|
public class CustomBiomeSource extends BiomeSource {
|
||||||
|
|
||||||
|
private final long seed;
|
||||||
|
private final Engine engine;
|
||||||
|
private final Registry<Biome> biomeCustomRegistry;
|
||||||
|
private final Registry<Biome> biomeRegistry;
|
||||||
|
private final AtomicCache<RegistryAccess> registryAccess = new AtomicCache<>();
|
||||||
|
private final RNG rng;
|
||||||
|
private final KMap<String, Holder<Biome>> customBiomes;
|
||||||
|
|
||||||
|
public CustomBiomeSource(long seed, Engine engine, World world) {
|
||||||
|
this.engine = engine;
|
||||||
|
this.seed = seed;
|
||||||
|
this.biomeCustomRegistry = registry().registry(Registries.BIOME).orElse(null);
|
||||||
|
this.biomeRegistry = ((RegistryAccess) getFor(RegistryAccess.Frozen.class, ((CraftServer) Bukkit.getServer()).getHandle().getServer())).registry(Registries.BIOME).orElse(null);
|
||||||
|
this.rng = new RNG(engine.getSeedManager().getBiome());
|
||||||
|
this.customBiomes = fillCustomBiomes(biomeCustomRegistry, engine);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static List<Holder<Biome>> getAllBiomes(Registry<Biome> customRegistry, Registry<Biome> registry, Engine engine) {
|
||||||
|
List<Holder<Biome>> b = new ArrayList<>();
|
||||||
|
|
||||||
|
for (IrisBiome i : engine.getAllBiomes()) {
|
||||||
|
if (i.isCustom()) {
|
||||||
|
for (IrisBiomeCustom j : i.getCustomDerivitives()) {
|
||||||
|
b.add(customRegistry.getHolder(customRegistry.getResourceKey(customRegistry
|
||||||
|
.get(new ResourceLocation(engine.getDimension().getLoadKey() + ":" + j.getId()))).get()).get());
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
b.add(CraftBlock.biomeToBiomeBase(registry, i.getVanillaDerivative()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return b;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Object getFor(Class<?> type, Object source) {
|
||||||
|
Object o = fieldFor(type, source);
|
||||||
|
|
||||||
|
if (o != null) {
|
||||||
|
return o;
|
||||||
|
}
|
||||||
|
|
||||||
|
return invokeFor(type, source);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Object fieldFor(Class<?> returns, Object in) {
|
||||||
|
return fieldForClass(returns, in.getClass(), in);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Object invokeFor(Class<?> returns, Object in) {
|
||||||
|
for (Method i : in.getClass().getMethods()) {
|
||||||
|
if (i.getReturnType().equals(returns)) {
|
||||||
|
i.setAccessible(true);
|
||||||
|
try {
|
||||||
|
Iris.debug("[NMS] Found " + returns.getSimpleName() + " in " + in.getClass().getSimpleName() + "." + i.getName() + "()");
|
||||||
|
return i.invoke(in);
|
||||||
|
} catch (Throwable e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
private static <T> T fieldForClass(Class<T> returnType, Class<?> sourceType, Object in) {
|
||||||
|
for (Field i : sourceType.getDeclaredFields()) {
|
||||||
|
if (i.getType().equals(returnType)) {
|
||||||
|
i.setAccessible(true);
|
||||||
|
try {
|
||||||
|
Iris.debug("[NMS] Found " + returnType.getSimpleName() + " in " + sourceType.getSimpleName() + "." + i.getName());
|
||||||
|
return (T) i.get(in);
|
||||||
|
} catch (IllegalAccessException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected Stream<Holder<Biome>> collectPossibleBiomes() {
|
||||||
|
return getAllBiomes(
|
||||||
|
((RegistryAccess) getFor(RegistryAccess.Frozen.class, ((CraftServer) Bukkit.getServer()).getHandle().getServer()))
|
||||||
|
.registry(Registries.BIOME).orElse(null),
|
||||||
|
((CraftWorld) engine.getWorld().realWorld()).getHandle().registryAccess().registry(Registries.BIOME).orElse(null),
|
||||||
|
engine).stream();
|
||||||
|
}
|
||||||
|
private KMap<String, Holder<Biome>> fillCustomBiomes(Registry<Biome> customRegistry, Engine engine) {
|
||||||
|
KMap<String, Holder<Biome>> m = new KMap<>();
|
||||||
|
|
||||||
|
for (IrisBiome i : engine.getAllBiomes()) {
|
||||||
|
if (i.isCustom()) {
|
||||||
|
for (IrisBiomeCustom j : i.getCustomDerivitives()) {
|
||||||
|
ResourceLocation resourceLocation = new ResourceLocation(engine.getDimension().getLoadKey() + ":" + j.getId());
|
||||||
|
Biome biome = customRegistry.get(resourceLocation);
|
||||||
|
Optional<ResourceKey<Biome>> optionalBiomeKey = customRegistry.getResourceKey(biome);
|
||||||
|
if (optionalBiomeKey.isEmpty()) {
|
||||||
|
Iris.error("Cannot find biome for IrisBiomeCustom " + j.getId() + " from engine " + engine.getName());
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
ResourceKey<Biome> biomeKey = optionalBiomeKey.get();
|
||||||
|
Optional<Holder.Reference<Biome>> optionalReferenceHolder = customRegistry.getHolder(biomeKey);
|
||||||
|
if (optionalReferenceHolder.isEmpty()) {
|
||||||
|
Iris.error("Cannot find reference to biome " + biomeKey + " for engine " + engine.getName());
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
m.put(j.getId(), optionalReferenceHolder.get());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return m;
|
||||||
|
}
|
||||||
|
|
||||||
|
private RegistryAccess registry() {
|
||||||
|
return registryAccess.aquire(() -> (RegistryAccess) getFor(RegistryAccess.Frozen.class, ((CraftServer) Bukkit.getServer()).getHandle().getServer()));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected Codec<? extends BiomeSource> codec() {
|
||||||
|
throw new UnsupportedOperationException("Not supported");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Holder<Biome> getNoiseBiome(int x, int y, int z, Climate.Sampler sampler) {
|
||||||
|
int m = (y - engine.getMinHeight()) << 2;
|
||||||
|
IrisBiome ib = engine.getComplex().getTrueBiomeStream().get(x << 2, z << 2);
|
||||||
|
if (ib.isCustom()) {
|
||||||
|
return customBiomes.get(ib.getCustomBiome(rng, x << 2, m, z << 2).getId());
|
||||||
|
} else {
|
||||||
|
org.bukkit.block.Biome v = ib.getSkyBiome(rng, x << 2, m, z << 2);
|
||||||
|
return CraftBlock.biomeToBiomeBase(biomeRegistry, v);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -16,49 +16,43 @@
|
|||||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package com.volmit.iris.core.nms.v19_1;
|
package com.volmit.iris.core.nms.v20;
|
||||||
|
|
||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.nms.INMSBinding;
|
import com.volmit.iris.core.nms.INMSBinding;
|
||||||
import com.volmit.iris.engine.data.cache.AtomicCache;
|
import com.volmit.iris.engine.data.cache.AtomicCache;
|
||||||
import com.volmit.iris.util.collection.KMap;
|
import com.volmit.iris.util.collection.KMap;
|
||||||
|
import com.volmit.iris.util.hunk.Hunk;
|
||||||
|
import com.volmit.iris.util.mantle.Mantle;
|
||||||
|
import com.volmit.iris.util.matter.MatterBiomeInject;
|
||||||
import com.volmit.iris.util.nbt.io.NBTUtil;
|
import com.volmit.iris.util.nbt.io.NBTUtil;
|
||||||
import com.volmit.iris.util.nbt.mca.NBTWorld;
|
import com.volmit.iris.util.nbt.mca.NBTWorld;
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCABiomeContainer;
|
import com.volmit.iris.util.nbt.mca.palette.*;
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAChunkBiomeContainer;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAGlobalPalette;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAIdMap;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAIdMapper;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAPalette;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAPaletteAccess;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAPalettedContainer;
|
|
||||||
import com.volmit.iris.util.nbt.mca.palette.MCAWrappedPalettedContainer;
|
|
||||||
import com.volmit.iris.util.nbt.tag.CompoundTag;
|
import com.volmit.iris.util.nbt.tag.CompoundTag;
|
||||||
import it.unimi.dsi.fastutil.objects.Object2IntMap;
|
import it.unimi.dsi.fastutil.objects.Object2IntMap;
|
||||||
import net.minecraft.core.*;
|
import net.minecraft.core.BlockPos;
|
||||||
|
import net.minecraft.core.Holder;
|
||||||
|
import net.minecraft.core.Registry;
|
||||||
|
import net.minecraft.core.RegistryAccess;
|
||||||
|
import net.minecraft.core.registries.Registries;
|
||||||
import net.minecraft.nbt.NbtIo;
|
import net.minecraft.nbt.NbtIo;
|
||||||
import net.minecraft.resources.ResourceLocation;
|
import net.minecraft.resources.ResourceLocation;
|
||||||
import net.minecraft.util.BitStorage;
|
|
||||||
import net.minecraft.util.Mth;
|
|
||||||
import net.minecraft.world.level.block.Block;
|
import net.minecraft.world.level.block.Block;
|
||||||
import net.minecraft.world.level.block.entity.BlockEntity;
|
import net.minecraft.world.level.block.entity.BlockEntity;
|
||||||
import net.minecraft.world.level.block.state.BlockState;
|
import net.minecraft.world.level.block.state.BlockState;
|
||||||
import net.minecraft.world.level.chunk.ChunkAccess;
|
import net.minecraft.world.level.chunk.ChunkAccess;
|
||||||
import net.minecraft.world.level.chunk.LevelChunkSection;
|
import net.minecraft.world.level.chunk.ChunkStatus;
|
||||||
import net.minecraft.world.level.chunk.Palette;
|
import net.minecraft.world.level.chunk.LevelChunk;
|
||||||
import net.minecraft.world.level.chunk.PalettedContainer;
|
import org.bukkit.*;
|
||||||
import org.bukkit.Bukkit;
|
|
||||||
import org.bukkit.Location;
|
|
||||||
import org.bukkit.Material;
|
|
||||||
import org.bukkit.World;
|
|
||||||
import org.bukkit.block.Biome;
|
import org.bukkit.block.Biome;
|
||||||
import org.bukkit.block.data.BlockData;
|
import org.bukkit.block.data.BlockData;
|
||||||
|
|
||||||
|
import org.bukkit.craftbukkit.v1_20_R1.CraftChunk;
|
||||||
import org.bukkit.craftbukkit.v1_19_R1.CraftServer;
|
import org.bukkit.craftbukkit.v1_20_R1.CraftServer;
|
||||||
import org.bukkit.craftbukkit.v1_19_R1.CraftWorld;
|
import org.bukkit.craftbukkit.v1_20_R1.CraftWorld;
|
||||||
import org.bukkit.craftbukkit.v1_19_R1.block.data.CraftBlockData;
|
import org.bukkit.craftbukkit.v1_20_R1.block.CraftBlock;
|
||||||
|
import org.bukkit.craftbukkit.v1_20_R1.block.data.CraftBlockData;
|
||||||
import org.bukkit.entity.Entity;
|
import org.bukkit.entity.Entity;
|
||||||
import org.bukkit.generator.ChunkGenerator;
|
import org.bukkit.generator.ChunkGenerator;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
@@ -68,14 +62,14 @@ import java.io.ByteArrayOutputStream;
|
|||||||
import java.io.DataInputStream;
|
import java.io.DataInputStream;
|
||||||
import java.io.DataOutputStream;
|
import java.io.DataOutputStream;
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.lang.reflect.InvocationTargetException;
|
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
|
|
||||||
public class NMSBinding19_1 implements INMSBinding {
|
public class NMSBinding1_20_1 implements INMSBinding {
|
||||||
|
|
||||||
|
public static final String NMS_VERSION = "1.20.1";
|
||||||
private final KMap<Biome, Object> baseBiomeCache = new KMap<>();
|
private final KMap<Biome, Object> baseBiomeCache = new KMap<>();
|
||||||
private final BlockData AIR = Material.AIR.createBlockData();
|
private final BlockData AIR = Material.AIR.createBlockData();
|
||||||
private final AtomicCache<MCAIdMap<net.minecraft.world.level.biome.Biome>> biomeMapCache = new AtomicCache<>();
|
private final AtomicCache<MCAIdMap<net.minecraft.world.level.biome.Biome>> biomeMapCache = new AtomicCache<>();
|
||||||
@@ -85,6 +79,56 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
private final AtomicCache<Method> byIdRef = new AtomicCache<>();
|
private final AtomicCache<Method> byIdRef = new AtomicCache<>();
|
||||||
private Field biomeStorageCache = null;
|
private Field biomeStorageCache = null;
|
||||||
|
|
||||||
|
private static Object getFor(Class<?> type, Object source) {
|
||||||
|
Object o = fieldFor(type, source);
|
||||||
|
|
||||||
|
if (o != null) {
|
||||||
|
return o;
|
||||||
|
}
|
||||||
|
|
||||||
|
return invokeFor(type, source);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Object invokeFor(Class<?> returns, Object in) {
|
||||||
|
for (Method i : in.getClass().getMethods()) {
|
||||||
|
if (i.getReturnType().equals(returns)) {
|
||||||
|
i.setAccessible(true);
|
||||||
|
try {
|
||||||
|
Iris.debug("[NMS] Found " + returns.getSimpleName() + " in " + in.getClass().getSimpleName() + "." + i.getName() + "()");
|
||||||
|
return i.invoke(in);
|
||||||
|
} catch (Throwable e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Object fieldFor(Class<?> returns, Object in) {
|
||||||
|
return fieldForClass(returns, in.getClass(), in);
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
private static <T> T fieldForClass(Class<T> returnType, Class<?> sourceType, Object in) {
|
||||||
|
for (Field i : sourceType.getDeclaredFields()) {
|
||||||
|
if (i.getType().equals(returnType)) {
|
||||||
|
i.setAccessible(true);
|
||||||
|
try {
|
||||||
|
Iris.debug("[NMS] Found " + returnType.getSimpleName() + " in " + sourceType.getSimpleName() + "." + i.getName());
|
||||||
|
return (T) i.get(in);
|
||||||
|
} catch (IllegalAccessException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static Class<?> getClassType(Class<?> type, int ordinal) {
|
||||||
|
return type.getDeclaredClasses()[ordinal];
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean hasTile(Location l) {
|
public boolean hasTile(Location l) {
|
||||||
return ((CraftWorld) l.getWorld()).getHandle().getBlockEntity(new BlockPos(l.getBlockX(), l.getBlockY(), l.getBlockZ()), false) != null;
|
return ((CraftWorld) l.getWorld()).getHandle().getBlockEntity(new BlockPos(l.getBlockX(), l.getBlockY(), l.getBlockZ()), false) != null;
|
||||||
@@ -94,7 +138,7 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
public CompoundTag serializeTile(Location location) {
|
public CompoundTag serializeTile(Location location) {
|
||||||
BlockEntity e = ((CraftWorld) location.getWorld()).getHandle().getBlockEntity(new BlockPos(location.getBlockX(), location.getBlockY(), location.getBlockZ()), true);
|
BlockEntity e = ((CraftWorld) location.getWorld()).getHandle().getBlockEntity(new BlockPos(location.getBlockX(), location.getBlockY(), location.getBlockZ()), true);
|
||||||
|
|
||||||
if(e == null) {
|
if (e == null) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -109,7 +153,7 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
tag.write(dos);
|
tag.write(dos);
|
||||||
dos.close();
|
dos.close();
|
||||||
return (CompoundTag) NBTUtil.read(new ByteArrayInputStream(boas.toByteArray()), false).getTag();
|
return (CompoundTag) NBTUtil.read(new ByteArrayInputStream(boas.toByteArray()), false).getTag();
|
||||||
} catch(Throwable ex) {
|
} catch (Throwable ex) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -124,7 +168,7 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
net.minecraft.nbt.CompoundTag c = NbtIo.read(din);
|
net.minecraft.nbt.CompoundTag c = NbtIo.read(din);
|
||||||
din.close();
|
din.close();
|
||||||
return c;
|
return c;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -156,33 +200,16 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private Registry<net.minecraft.world.level.biome.Biome> getCustomBiomeRegistry() {
|
private Registry<net.minecraft.world.level.biome.Biome> getCustomBiomeRegistry() {
|
||||||
|
return registry().registry(Registries.BIOME).orElse(null);
|
||||||
return registry().registry(Registry.BIOME_REGISTRY).orElse(null);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private Registry<Block> getBlockRegistry() {
|
private Registry<Block> getBlockRegistry() {
|
||||||
return registry().registry(Registry.BLOCK_REGISTRY).orElse(null);
|
return registry().registry(Registries.BLOCK).orElse(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object getBiomeBaseFromId(int id) {
|
public Object getBiomeBaseFromId(int id) {
|
||||||
try {
|
return getCustomBiomeRegistry().getHolder(id);
|
||||||
return byIdRef.aquire(() -> {
|
|
||||||
for(Method i : IdMap.class.getDeclaredMethods()) {
|
|
||||||
if(i.getParameterCount() == 1 && i.getParameterTypes()[0].equals(int.class)) {
|
|
||||||
Iris.info("[NMS] Found byId method in " + IdMap.class.getSimpleName() + "." + i.getName() + "(int) => " + Biome.class.getSimpleName());
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Iris.error("Cannot find byId method!");
|
|
||||||
return null;
|
|
||||||
}).invoke(getCustomBiomeRegistry(), id);
|
|
||||||
} catch(IllegalAccessException | InvocationTargetException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -197,7 +224,7 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getTrueBiomeBaseId(Object biomeBase) {
|
public int getTrueBiomeBaseId(Object biomeBase) {
|
||||||
return getCustomBiomeRegistry().getId((net.minecraft.world.level.biome.Biome) biomeBase);
|
return getCustomBiomeRegistry().getId(((Holder<net.minecraft.world.level.biome.Biome>) biomeBase).value());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -214,11 +241,16 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
public Object getCustomBiomeBaseFor(String mckey) {
|
public Object getCustomBiomeBaseFor(String mckey) {
|
||||||
return getCustomBiomeRegistry().get(new ResourceLocation(mckey));
|
return getCustomBiomeRegistry().get(new ResourceLocation(mckey));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object getCustomBiomeBaseHolderFor(String mckey) {
|
public Object getCustomBiomeBaseHolderFor(String mckey) {
|
||||||
return getCustomBiomeRegistry().getHolder(getTrueBiomeBaseId(getCustomBiomeRegistry().get(new ResourceLocation(mckey)))).get();
|
return getCustomBiomeRegistry().getHolder(getTrueBiomeBaseId(getCustomBiomeRegistry().get(new ResourceLocation(mckey)))).get();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public int getBiomeBaseIdForKey(String key) {
|
||||||
|
return getCustomBiomeRegistry().getId(getCustomBiomeRegistry().get(new ResourceLocation(key)));
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getKeyForBiomeBase(Object biomeBase) {
|
public String getKeyForBiomeBase(Object biomeBase) {
|
||||||
return getCustomBiomeRegistry().getKey((net.minecraft.world.level.biome.Biome) biomeBase).getPath(); // something, not something:something
|
return getCustomBiomeRegistry().getKey((net.minecraft.world.level.biome.Biome) biomeBase).getPath(); // something, not something:something
|
||||||
@@ -226,24 +258,25 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object getBiomeBase(World world, Biome biome) {
|
public Object getBiomeBase(World world, Biome biome) {
|
||||||
return getBiomeBase(((CraftWorld) world).getHandle().registryAccess().registry(Registry.BIOME_REGISTRY).orElse(null), biome);
|
return CraftBlock.biomeToBiomeBase(((CraftWorld) world).getHandle()
|
||||||
|
.registryAccess().registry(Registries.BIOME).orElse(null), biome);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object getBiomeBase(Object registry, Biome biome) {
|
public Object getBiomeBase(Object registry, Biome biome) {
|
||||||
Object v = baseBiomeCache.get(biome);
|
Object v = baseBiomeCache.get(biome);
|
||||||
|
|
||||||
if(v != null) {
|
if (v != null) {
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
//noinspection unchecked
|
//noinspection unchecked
|
||||||
v = org.bukkit.craftbukkit.v1_19_R1.block.CraftBlock.biomeToBiomeBase((Registry<net.minecraft.world.level.biome.Biome>) registry, biome);
|
v = CraftBlock.biomeToBiomeBase((Registry<net.minecraft.world.level.biome.Biome>) registry, biome);
|
||||||
if(v == null) {
|
if (v == null) {
|
||||||
// Ok so there is this new biome name called "CUSTOM" in Paper's new releases.
|
// Ok so there is this new biome name called "CUSTOM" in Paper's new releases.
|
||||||
// But, this does NOT exist within CraftBukkit which makes it return an error.
|
// But, this does NOT exist within CraftBukkit which makes it return an error.
|
||||||
// So, we will just return the ID that the plains biome returns instead.
|
// So, we will just return the ID that the plains biome returns instead.
|
||||||
//noinspection unchecked
|
//noinspection unchecked
|
||||||
return org.bukkit.craftbukkit.v1_19_R1.block.CraftBlock.biomeToBiomeBase((Registry<net.minecraft.world.level.biome.Biome>) registry, Biome.PLAINS);
|
return CraftBlock.biomeToBiomeBase((Registry<net.minecraft.world.level.biome.Biome>) registry, Biome.PLAINS);
|
||||||
}
|
}
|
||||||
baseBiomeCache.put(biome, v);
|
baseBiomeCache.put(biome, v);
|
||||||
return v;
|
return v;
|
||||||
@@ -256,9 +289,9 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getBiomeId(Biome biome) {
|
public int getBiomeId(Biome biome) {
|
||||||
for(World i : Bukkit.getWorlds()) {
|
for (World i : Bukkit.getWorlds()) {
|
||||||
if(i.getEnvironment().equals(World.Environment.NORMAL)) {
|
if (i.getEnvironment().equals(World.Environment.NORMAL)) {
|
||||||
Registry<net.minecraft.world.level.biome.Biome> registry = ((CraftWorld) i).getHandle().registryAccess().registry(Registry.BIOME_REGISTRY).orElse(null);
|
Registry<net.minecraft.world.level.biome.Biome> registry = ((CraftWorld) i).getHandle().registryAccess().registry(Registries.BIOME).orElse(null);
|
||||||
return registry.getId((net.minecraft.world.level.biome.Biome) getBiomeBase(registry, biome));
|
return registry.getId((net.minecraft.world.level.biome.Biome) getBiomeBase(registry, biome));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -323,7 +356,7 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
AtomicInteger a = new AtomicInteger(0);
|
AtomicInteger a = new AtomicInteger(0);
|
||||||
|
|
||||||
getCustomBiomeRegistry().keySet().forEach((i) -> {
|
getCustomBiomeRegistry().keySet().forEach((i) -> {
|
||||||
if(i.getNamespace().equals("minecraft")) {
|
if (i.getNamespace().equals("minecraft")) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -338,62 +371,35 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void setBiomes(int cx, int cz, World world, Hunk<Object> biomes) {
|
||||||
|
LevelChunk c = ((CraftWorld) world).getHandle().getChunk(cx, cz);
|
||||||
|
biomes.iterateSync((x, y, z, b) -> c.setBiome(x, y, z, (Holder<net.minecraft.world.level.biome.Biome>) b));
|
||||||
|
c.setUnsaved(true);
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void forceBiomeInto(int x, int y, int z, Object somethingVeryDirty, ChunkGenerator.BiomeGrid chunk) {
|
public void forceBiomeInto(int x, int y, int z, Object somethingVeryDirty, ChunkGenerator.BiomeGrid chunk) {
|
||||||
try {
|
try {
|
||||||
ChunkAccess s = (ChunkAccess) getFieldForBiomeStorage(chunk).get(chunk);
|
ChunkAccess s = (ChunkAccess) getFieldForBiomeStorage(chunk).get(chunk);
|
||||||
Holder<net.minecraft.world.level.biome.Biome> biome = (Holder<net.minecraft.world.level.biome.Biome>) somethingVeryDirty;
|
Holder<net.minecraft.world.level.biome.Biome> biome = (Holder<net.minecraft.world.level.biome.Biome>) somethingVeryDirty;
|
||||||
s.setBiome(x, y, z, biome);
|
s.setBiome(x, y, z, biome);
|
||||||
/*int l = QuartPos.fromBlock(s.getMinBuildHeight());
|
} catch (IllegalAccessException e) {
|
||||||
int i1 = l + QuartPos.fromBlock(s.getHeight()) - 1;
|
|
||||||
PalettedContainer<Holder<net.minecraft.world.level.biome.Biome>> palette = getPalette(s, s.getSectionIndex(QuartPos.toBlock(Mth.clamp(y, l, i1))));
|
|
||||||
int index = getPaletteIndex(x, y, z, s, palette);
|
|
||||||
int data = getPaletteDataId(palette, biome);
|
|
||||||
setPaletteData(palette, index, data);*/
|
|
||||||
} catch(IllegalAccessException e) {
|
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private PalettedContainer<Holder<net.minecraft.world.level.biome.Biome>> getPalette(ChunkAccess ca, int index) {
|
|
||||||
LevelChunkSection[] sections = fieldForClass(LevelChunkSection[].class, ChunkAccess.class, ca);
|
|
||||||
return fieldForClass(PalettedContainer.class, LevelChunkSection.class, sections[index]);
|
|
||||||
}
|
|
||||||
|
|
||||||
private int getPaletteIndex(int x, int y, int z, ChunkAccess s, PalettedContainer<?> palette) {
|
|
||||||
int l = QuartPos.fromBlock(s.getMinBuildHeight());
|
|
||||||
int i1 = l + QuartPos.fromBlock(s.getHeight()) - 1;
|
|
||||||
int j1 = Mth.clamp(y, l, i1);
|
|
||||||
return fieldForClass(PalettedContainer.Strategy.class, PalettedContainer.class, palette).getIndex(x & 3, j1 & 3, z & 3);
|
|
||||||
}
|
|
||||||
|
|
||||||
private <T extends Holder<?>> int getPaletteDataId(PalettedContainer<T> palette, T data) throws ClassNotFoundException {
|
|
||||||
Class<?> dataType = getClassType(PalettedContainer.class, 1);
|
|
||||||
Object paletteData = fieldFor(dataType, palette);
|
|
||||||
Palette<T> fuckinFinally = fieldForClass(Palette.class,dataType, paletteData);
|
|
||||||
return fuckinFinally.idFor(data);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void setPaletteData(PalettedContainer<?> palette, int index, int data) throws ClassNotFoundException {
|
|
||||||
Class<?> dataType = getClassType(PalettedContainer.class, 1);
|
|
||||||
Object paletteData = fieldFor(dataType, palette);
|
|
||||||
BitStorage storage = fieldForClass(BitStorage.class, dataType, paletteData);
|
|
||||||
storage.set(index, data);
|
|
||||||
}
|
|
||||||
|
|
||||||
private Field getFieldForBiomeStorage(Object storage) {
|
private Field getFieldForBiomeStorage(Object storage) {
|
||||||
Field f = biomeStorageCache;
|
Field f = biomeStorageCache;
|
||||||
|
|
||||||
if(f != null) {
|
if (f != null) {
|
||||||
return f;
|
return f;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
|
|
||||||
f = storage.getClass().getDeclaredField("biome");
|
f = storage.getClass().getDeclaredField("biome");
|
||||||
f.setAccessible(true);
|
f.setAccessible(true);
|
||||||
return f;
|
return f;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
Iris.error(storage.getClass().getCanonicalName());
|
Iris.error(storage.getClass().getCanonicalName());
|
||||||
@@ -420,61 +426,29 @@ public class NMSBinding19_1 implements INMSBinding {
|
|||||||
});
|
});
|
||||||
MCAPalette<BlockState> global = globalCache.aquireNasty(() -> new MCAGlobalPalette<>(registry, ((CraftBlockData) AIR).getState()));
|
MCAPalette<BlockState> global = globalCache.aquireNasty(() -> new MCAGlobalPalette<>(registry, ((CraftBlockData) AIR).getState()));
|
||||||
MCAPalettedContainer<BlockState> container = new MCAPalettedContainer<>(global, registry,
|
MCAPalettedContainer<BlockState> container = new MCAPalettedContainer<>(global, registry,
|
||||||
i -> ((CraftBlockData) NBTWorld.getBlockData(i)).getState(),
|
i -> ((CraftBlockData) NBTWorld.getBlockData(i)).getState(),
|
||||||
i -> NBTWorld.getCompound(CraftBlockData.fromData(i)),
|
i -> NBTWorld.getCompound(CraftBlockData.fromData(i)),
|
||||||
((CraftBlockData) AIR).getState());
|
((CraftBlockData) AIR).getState());
|
||||||
return new MCAWrappedPalettedContainer<>(container,
|
return new MCAWrappedPalettedContainer<>(container,
|
||||||
i -> NBTWorld.getCompound(CraftBlockData.fromData(i)),
|
i -> NBTWorld.getCompound(CraftBlockData.fromData(i)),
|
||||||
i -> ((CraftBlockData) NBTWorld.getBlockData(i)).getState());
|
i -> ((CraftBlockData) NBTWorld.getBlockData(i)).getState());
|
||||||
}
|
}
|
||||||
|
|
||||||
private static Object getFor(Class<?> type, Object source) {
|
@Override
|
||||||
Object o = fieldFor(type, source);
|
public void injectBiomesFromMantle(Chunk e, Mantle mantle) {
|
||||||
|
ChunkAccess chunk = ((CraftChunk) e).getHandle(ChunkStatus.FULL);
|
||||||
if(o != null) {
|
AtomicInteger c = new AtomicInteger();
|
||||||
return o;
|
AtomicInteger r = new AtomicInteger();
|
||||||
}
|
mantle.iterateChunk(e.getX(), e.getZ(), MatterBiomeInject.class, (x, y, z, b) -> {
|
||||||
|
if (b != null) {
|
||||||
return invokeFor(type, source);
|
if (b.isCustom()) {
|
||||||
}
|
chunk.setBiome(x, y, z, getCustomBiomeRegistry().getHolder(b.getBiomeId()).get());
|
||||||
|
c.getAndIncrement();
|
||||||
private static Object invokeFor(Class<?> returns, Object in) {
|
} else {
|
||||||
for(Method i : in.getClass().getMethods()) {
|
chunk.setBiome(x, y, z, (Holder<net.minecraft.world.level.biome.Biome>) getBiomeBase(e.getWorld(), b.getBiome()));
|
||||||
if(i.getReturnType().equals(returns)) {
|
r.getAndIncrement();
|
||||||
i.setAccessible(true);
|
|
||||||
try {
|
|
||||||
Iris.debug("[NMS] Found " + returns.getSimpleName() + " in " + in.getClass().getSimpleName() + "." + i.getName() + "()");
|
|
||||||
return i.invoke(in);
|
|
||||||
} catch(Throwable e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
});
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static Object fieldFor(Class<?> returns, Object in) {
|
|
||||||
return fieldForClass(returns, in.getClass(), in);
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
private static <T> T fieldForClass(Class<T> returnType, Class<?> sourceType, Object in) {
|
|
||||||
for(Field i : sourceType.getDeclaredFields()) {
|
|
||||||
if(i.getType().equals(returnType)) {
|
|
||||||
i.setAccessible(true);
|
|
||||||
try {
|
|
||||||
Iris.debug("[NMS] Found " + returnType.getSimpleName() + " in " + sourceType.getSimpleName() + "." + i.getName());
|
|
||||||
return (T) i.get(in);
|
|
||||||
} catch(IllegalAccessException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static Class<?> getClassType(Class<?> type, int ordinal) {
|
|
||||||
return type.getDeclaredClasses()[ordinal];
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -54,8 +54,7 @@ public class IrisPack {
|
|||||||
* Create an iris pack backed by a data folder
|
* Create an iris pack backed by a data folder
|
||||||
* the data folder is assumed to be in the Iris/packs/NAME folder
|
* the data folder is assumed to be in the Iris/packs/NAME folder
|
||||||
*
|
*
|
||||||
* @param name
|
* @param name the name
|
||||||
* the name
|
|
||||||
*/
|
*/
|
||||||
public IrisPack(String name) {
|
public IrisPack(String name) {
|
||||||
this(packsPack(name));
|
this(packsPack(name));
|
||||||
@@ -64,17 +63,16 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Create an iris pack backed by a data folder
|
* Create an iris pack backed by a data folder
|
||||||
*
|
*
|
||||||
* @param folder
|
* @param folder the folder of the pack. Must be a directory
|
||||||
* the folder of the pack. Must be a directory
|
|
||||||
*/
|
*/
|
||||||
public IrisPack(File folder) {
|
public IrisPack(File folder) {
|
||||||
this.folder = folder;
|
this.folder = folder;
|
||||||
|
|
||||||
if(!folder.exists()) {
|
if (!folder.exists()) {
|
||||||
throw new RuntimeException("Cannot open Pack " + folder.getPath() + " (directory doesnt exist)");
|
throw new RuntimeException("Cannot open Pack " + folder.getPath() + " (directory doesnt exist)");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!folder.isDirectory()) {
|
if (!folder.isDirectory()) {
|
||||||
throw new RuntimeException("Cannot open Pack " + folder.getPath() + " (not a directory)");
|
throw new RuntimeException("Cannot open Pack " + folder.getPath() + " (not a directory)");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -84,23 +82,20 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Create a new pack from the input url
|
* Create a new pack from the input url
|
||||||
*
|
*
|
||||||
* @param sender
|
* @param sender the sender
|
||||||
* the sender
|
* @param url the url, or name, or really anything see IrisPackRepository.from(String)
|
||||||
* @param url
|
|
||||||
* the url, or name, or really anything see IrisPackRepository.from(String)
|
|
||||||
* @return the iris pack
|
* @return the iris pack
|
||||||
* @throws IrisException
|
* @throws IrisException fails
|
||||||
* fails
|
|
||||||
*/
|
*/
|
||||||
public static Future<IrisPack> from(VolmitSender sender, String url) throws IrisException {
|
public static Future<IrisPack> from(VolmitSender sender, String url) throws IrisException {
|
||||||
IrisPackRepository repo = IrisPackRepository.from(url);
|
IrisPackRepository repo = IrisPackRepository.from(url);
|
||||||
if(repo == null) {
|
if (repo == null) {
|
||||||
throw new IrisException("Null Repo");
|
throw new IrisException("Null Repo");
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
return from(sender, repo);
|
return from(sender, repo);
|
||||||
} catch(MalformedURLException e) {
|
} catch (MalformedURLException e) {
|
||||||
throw new IrisException("Malformed URL " + e.getMessage());
|
throw new IrisException("Malformed URL " + e.getMessage());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -108,13 +103,10 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Create a pack from a repo
|
* Create a pack from a repo
|
||||||
*
|
*
|
||||||
* @param sender
|
* @param sender the sender
|
||||||
* the sender
|
* @param repo the repo
|
||||||
* @param repo
|
|
||||||
* the repo
|
|
||||||
* @return the pack
|
* @return the pack
|
||||||
* @throws MalformedURLException
|
* @throws MalformedURLException shit happens
|
||||||
* shit happens
|
|
||||||
*/
|
*/
|
||||||
public static Future<IrisPack> from(VolmitSender sender, IrisPackRepository repo) throws MalformedURLException {
|
public static Future<IrisPack> from(VolmitSender sender, IrisPackRepository repo) throws MalformedURLException {
|
||||||
CompletableFuture<IrisPack> pack = new CompletableFuture<>();
|
CompletableFuture<IrisPack> pack = new CompletableFuture<>();
|
||||||
@@ -127,16 +119,14 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Create a blank pack with a given name
|
* Create a blank pack with a given name
|
||||||
*
|
*
|
||||||
* @param name
|
* @param name the name of the pack
|
||||||
* the name of the pack
|
|
||||||
* @return the pack
|
* @return the pack
|
||||||
* @throws IrisException
|
* @throws IrisException if the pack already exists or another error
|
||||||
* if the pack already exists or another error
|
|
||||||
*/
|
*/
|
||||||
public static IrisPack blank(String name) throws IrisException {
|
public static IrisPack blank(String name) throws IrisException {
|
||||||
File f = packsPack(name);
|
File f = packsPack(name);
|
||||||
|
|
||||||
if(f.exists()) {
|
if (f.exists()) {
|
||||||
throw new IrisException("Already exists");
|
throw new IrisException("Already exists");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -144,10 +134,10 @@ public class IrisPack {
|
|||||||
fd.getParentFile().mkdirs();
|
fd.getParentFile().mkdirs();
|
||||||
try {
|
try {
|
||||||
IO.writeAll(fd, "{\n" +
|
IO.writeAll(fd, "{\n" +
|
||||||
" \"name\": \"" + Form.capitalize(name) + "\",\n" +
|
" \"name\": \"" + Form.capitalize(name) + "\",\n" +
|
||||||
" \"version\": 1\n" +
|
" \"version\": 1\n" +
|
||||||
"}\n");
|
"}\n");
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
throw new IrisException(e.getMessage(), e);
|
throw new IrisException(e.getMessage(), e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -159,8 +149,7 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Get a packs pack folder for a name. Such that overworld would resolve as Iris/packs/overworld
|
* Get a packs pack folder for a name. Such that overworld would resolve as Iris/packs/overworld
|
||||||
*
|
*
|
||||||
* @param name
|
* @param name the name
|
||||||
* the name
|
|
||||||
* @return the file path
|
* @return the file path
|
||||||
*/
|
*/
|
||||||
public static File packsPack(String name) {
|
public static File packsPack(String name) {
|
||||||
@@ -170,11 +159,11 @@ public class IrisPack {
|
|||||||
private static KList<File> collectFiles(File f, String fileExtension) {
|
private static KList<File> collectFiles(File f, String fileExtension) {
|
||||||
KList<File> l = new KList<>();
|
KList<File> l = new KList<>();
|
||||||
|
|
||||||
if(f.isDirectory()) {
|
if (f.isDirectory()) {
|
||||||
for(File i : f.listFiles()) {
|
for (File i : f.listFiles()) {
|
||||||
l.addAll(collectFiles(i, fileExtension));
|
l.addAll(collectFiles(i, fileExtension));
|
||||||
}
|
}
|
||||||
} else if(f.getName().endsWith("." + fileExtension)) {
|
} else if (f.getName().endsWith("." + fileExtension)) {
|
||||||
l.add(f);
|
l.add(f);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -225,13 +214,13 @@ public class IrisPack {
|
|||||||
p.end();
|
p.end();
|
||||||
Iris.debug("Building Workspace: " + ws.getPath() + " took " + Form.duration(p.getMilliseconds(), 2));
|
Iris.debug("Building Workspace: " + ws.getPath() + " took " + Form.duration(p.getMilliseconds(), 2));
|
||||||
return true;
|
return true;
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
Iris.warn("Pack invalid: " + ws.getAbsolutePath() + " Re-creating. You may loose some vs-code workspace settings! But not your actual project!");
|
Iris.warn("Pack invalid: " + ws.getAbsolutePath() + " Re-creating. You may loose some vs-code workspace settings! But not your actual project!");
|
||||||
ws.delete();
|
ws.delete();
|
||||||
try {
|
try {
|
||||||
IO.writeAll(ws, generateWorkspaceConfig());
|
IO.writeAll(ws, generateWorkspaceConfig());
|
||||||
} catch(IOException e1) {
|
} catch (IOException e1) {
|
||||||
Iris.reportError(e1);
|
Iris.reportError(e1);
|
||||||
e1.printStackTrace();
|
e1.printStackTrace();
|
||||||
}
|
}
|
||||||
@@ -243,8 +232,7 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Install this pack into a world
|
* Install this pack into a world
|
||||||
*
|
*
|
||||||
* @param world
|
* @param world the world to install into (world/iris/pack)
|
||||||
* the world to install into (world/iris/pack)
|
|
||||||
* @return the installed pack
|
* @return the installed pack
|
||||||
*/
|
*/
|
||||||
public IrisPack install(World world) throws IrisException {
|
public IrisPack install(World world) throws IrisException {
|
||||||
@@ -254,8 +242,7 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Install this pack into a world
|
* Install this pack into a world
|
||||||
*
|
*
|
||||||
* @param world
|
* @param world the world to install into (world/iris/pack)
|
||||||
* the world to install into (world/iris/pack)
|
|
||||||
* @return the installed pack
|
* @return the installed pack
|
||||||
*/
|
*/
|
||||||
public IrisPack install(IrisWorld world) throws IrisException {
|
public IrisPack install(IrisWorld world) throws IrisException {
|
||||||
@@ -265,12 +252,11 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Install this pack into a world
|
* Install this pack into a world
|
||||||
*
|
*
|
||||||
* @param folder
|
* @param folder the folder to install this pack into
|
||||||
* the folder to install this pack into
|
|
||||||
* @return the installed pack
|
* @return the installed pack
|
||||||
*/
|
*/
|
||||||
public IrisPack install(File folder) throws IrisException {
|
public IrisPack install(File folder) throws IrisException {
|
||||||
if(folder.exists()) {
|
if (folder.exists()) {
|
||||||
throw new IrisException("Cannot install new pack because the folder " + folder.getName() + " already exists!");
|
throw new IrisException("Cannot install new pack because the folder " + folder.getName() + " already exists!");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -278,7 +264,7 @@ public class IrisPack {
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
FileUtils.copyDirectory(getFolder(), folder);
|
FileUtils.copyDirectory(getFolder(), folder);
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -289,20 +275,19 @@ public class IrisPack {
|
|||||||
* Create a new pack using this pack as a template. The new pack will be renamed & have a renamed dimension
|
* Create a new pack using this pack as a template. The new pack will be renamed & have a renamed dimension
|
||||||
* to match it.
|
* to match it.
|
||||||
*
|
*
|
||||||
* @param newName
|
* @param newName the new pack name
|
||||||
* the new pack name
|
|
||||||
* @return the new IrisPack
|
* @return the new IrisPack
|
||||||
*/
|
*/
|
||||||
public IrisPack install(String newName) throws IrisException {
|
public IrisPack install(String newName) throws IrisException {
|
||||||
File newPack = packsPack(newName);
|
File newPack = packsPack(newName);
|
||||||
|
|
||||||
if(newPack.exists()) {
|
if (newPack.exists()) {
|
||||||
throw new IrisException("Cannot install new pack because the folder " + newName + " already exists!");
|
throw new IrisException("Cannot install new pack because the folder " + newName + " already exists!");
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
FileUtils.copyDirectory(getFolder(), newPack);
|
FileUtils.copyDirectory(getFolder(), newPack);
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
Iris.reportError(e);
|
Iris.reportError(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -314,7 +299,7 @@ public class IrisPack {
|
|||||||
try {
|
try {
|
||||||
FileUtils.moveFile(from, to);
|
FileUtils.moveFile(from, to);
|
||||||
new File(newPack, getWorkspaceFile().getName()).delete();
|
new File(newPack, getWorkspaceFile().getName()).delete();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
throw new IrisException(e);
|
throw new IrisException(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -345,8 +330,7 @@ public class IrisPack {
|
|||||||
/**
|
/**
|
||||||
* Find all files in this pack with the given extension
|
* Find all files in this pack with the given extension
|
||||||
*
|
*
|
||||||
* @param fileExtension
|
* @param fileExtension the extension
|
||||||
* the extension
|
|
||||||
* @return the list of files
|
* @return the list of files
|
||||||
*/
|
*/
|
||||||
public KList<File> collectFiles(String fileExtension) {
|
public KList<File> collectFiles(String fileExtension) {
|
||||||
@@ -386,8 +370,8 @@ public class IrisPack {
|
|||||||
JSONArray schemas = new JSONArray();
|
JSONArray schemas = new JSONArray();
|
||||||
IrisData dm = IrisData.get(getFolder());
|
IrisData dm = IrisData.get(getFolder());
|
||||||
|
|
||||||
for(ResourceLoader<?> r : dm.getLoaders().v()) {
|
for (ResourceLoader<?> r : dm.getLoaders().v()) {
|
||||||
if(r.supportsSchemas()) {
|
if (r.supportsSchemas()) {
|
||||||
schemas.put(r.buildSchema());
|
schemas.put(r.buildSchema());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,34 +55,34 @@ public class IrisPackRepository {
|
|||||||
*/
|
*/
|
||||||
public static IrisPackRepository from(String g) {
|
public static IrisPackRepository from(String g) {
|
||||||
// https://github.com/IrisDimensions/overworld
|
// https://github.com/IrisDimensions/overworld
|
||||||
if(g.startsWith("https://github.com/")) {
|
if (g.startsWith("https://github.com/")) {
|
||||||
String sub = g.split("\\Qgithub.com/\\E")[1];
|
String sub = g.split("\\Qgithub.com/\\E")[1];
|
||||||
IrisPackRepository r = IrisPackRepository.builder()
|
IrisPackRepository r = IrisPackRepository.builder()
|
||||||
.user(sub.split("\\Q/\\E")[0])
|
.user(sub.split("\\Q/\\E")[0])
|
||||||
.repo(sub.split("\\Q/\\E")[1]).build();
|
.repo(sub.split("\\Q/\\E")[1]).build();
|
||||||
|
|
||||||
if(g.contains("/tree/")) {
|
if (g.contains("/tree/")) {
|
||||||
r.setBranch(g.split("/tree/")[1]);
|
r.setBranch(g.split("/tree/")[1]);
|
||||||
}
|
}
|
||||||
|
|
||||||
return r;
|
return r;
|
||||||
} else if(g.contains("/")) {
|
} else if (g.contains("/")) {
|
||||||
String[] f = g.split("\\Q/\\E");
|
String[] f = g.split("\\Q/\\E");
|
||||||
|
|
||||||
if(f.length == 1) {
|
if (f.length == 1) {
|
||||||
return from(g);
|
return from(g);
|
||||||
} else if(f.length == 2) {
|
} else if (f.length == 2) {
|
||||||
return IrisPackRepository.builder()
|
return IrisPackRepository.builder()
|
||||||
.user(f[0])
|
.user(f[0])
|
||||||
.repo(f[1])
|
.repo(f[1])
|
||||||
.build();
|
.build();
|
||||||
} else if(f.length >= 3) {
|
} else if (f.length >= 3) {
|
||||||
IrisPackRepository r = IrisPackRepository.builder()
|
IrisPackRepository r = IrisPackRepository.builder()
|
||||||
.user(f[0])
|
.user(f[0])
|
||||||
.repo(f[1])
|
.repo(f[1])
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
if(f[2].startsWith("#")) {
|
if (f[2].startsWith("#")) {
|
||||||
r.setTag(f[2].substring(1));
|
r.setTag(f[2].substring(1));
|
||||||
} else {
|
} else {
|
||||||
r.setBranch(f[2]);
|
r.setBranch(f[2]);
|
||||||
@@ -92,17 +92,17 @@ public class IrisPackRepository {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
return IrisPackRepository.builder()
|
return IrisPackRepository.builder()
|
||||||
.user("IrisDimensions")
|
.user("IrisDimensions")
|
||||||
.repo(g)
|
.repo(g)
|
||||||
.branch(g.equals("overworld") ? "stable" : "master")
|
.branch(g.equals("overworld") ? "stable" : "master")
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public String toURL() {
|
public String toURL() {
|
||||||
if(!tag.trim().isEmpty()) {
|
if (!tag.trim().isEmpty()) {
|
||||||
return "https://codeload.github.com/" + user + "/" + repo + "/zip/refs/tags/" + tag;
|
return "https://codeload.github.com/" + user + "/" + repo + "/zip/refs/tags/" + tag;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -112,19 +112,19 @@ public class IrisPackRepository {
|
|||||||
public void install(VolmitSender sender, Runnable whenComplete) throws MalformedURLException {
|
public void install(VolmitSender sender, Runnable whenComplete) throws MalformedURLException {
|
||||||
File pack = Iris.instance.getDataFolderNoCreate(StudioSVC.WORKSPACE_NAME, getRepo());
|
File pack = Iris.instance.getDataFolderNoCreate(StudioSVC.WORKSPACE_NAME, getRepo());
|
||||||
|
|
||||||
if(!pack.exists()) {
|
if (!pack.exists()) {
|
||||||
File dl = new File(Iris.getTemp(), "dltk-" + UUID.randomUUID() + ".zip");
|
File dl = new File(Iris.getTemp(), "dltk-" + UUID.randomUUID() + ".zip");
|
||||||
File work = new File(Iris.getTemp(), "extk-" + UUID.randomUUID());
|
File work = new File(Iris.getTemp(), "extk-" + UUID.randomUUID());
|
||||||
new JobCollection(Form.capitalize(getRepo()),
|
new JobCollection(Form.capitalize(getRepo()),
|
||||||
new DownloadJob(toURL(), pack),
|
new DownloadJob(toURL(), pack),
|
||||||
new SingleJob("Extracting", () -> ZipUtil.unpack(dl, work)),
|
new SingleJob("Extracting", () -> ZipUtil.unpack(dl, work)),
|
||||||
new SingleJob("Installing", () -> {
|
new SingleJob("Installing", () -> {
|
||||||
try {
|
try {
|
||||||
FileUtils.copyDirectory(work.listFiles()[0], pack);
|
FileUtils.copyDirectory(work.listFiles()[0], pack);
|
||||||
} catch(IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
})).execute(sender, whenComplete);
|
})).execute(sender, whenComplete);
|
||||||
} else {
|
} else {
|
||||||
sender.sendMessage("Pack already exists!");
|
sender.sendMessage("Pack already exists!");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,6 +55,7 @@ public class IrisPregenerator {
|
|||||||
private final KSet<Position2> retry;
|
private final KSet<Position2> retry;
|
||||||
private final KSet<Position2> net;
|
private final KSet<Position2> net;
|
||||||
private final ChronoLatch cl;
|
private final ChronoLatch cl;
|
||||||
|
private final ChronoLatch saveLatch = new ChronoLatch(30000);
|
||||||
|
|
||||||
public IrisPregenerator(PregenTask task, PregeneratorMethod generator, PregenListener listener) {
|
public IrisPregenerator(PregenTask task, PregeneratorMethod generator, PregenListener listener) {
|
||||||
this.listener = listenify(listener);
|
this.listener = listenify(listener);
|
||||||
@@ -85,7 +86,7 @@ public class IrisPregenerator {
|
|||||||
generatedLast.set(generated.get());
|
generatedLast.set(generated.get());
|
||||||
chunksPerSecond.put(secondGenerated);
|
chunksPerSecond.put(secondGenerated);
|
||||||
|
|
||||||
if(minuteLatch.flip()) {
|
if (minuteLatch.flip()) {
|
||||||
int minuteGenerated = generated.get() - generatedLastMinute.get();
|
int minuteGenerated = generated.get() - generatedLastMinute.get();
|
||||||
generatedLastMinute.set(generated.get());
|
generatedLastMinute.set(generated.get());
|
||||||
chunksPerMinute.put(minuteGenerated);
|
chunksPerMinute.put(minuteGenerated);
|
||||||
@@ -93,14 +94,15 @@ public class IrisPregenerator {
|
|||||||
}
|
}
|
||||||
|
|
||||||
listener.onTick(chunksPerSecond.getAverage(), chunksPerMinute.getAverage(),
|
listener.onTick(chunksPerSecond.getAverage(), chunksPerMinute.getAverage(),
|
||||||
regionsPerMinute.getAverage(),
|
regionsPerMinute.getAverage(),
|
||||||
(double) generated.get() / (double) totalChunks.get(),
|
(double) generated.get() / (double) totalChunks.get(),
|
||||||
generated.get(), totalChunks.get(),
|
generated.get(), totalChunks.get(),
|
||||||
totalChunks.get() - generated.get(),
|
totalChunks.get() - generated.get(),
|
||||||
eta, M.ms() - startTime.get(), currentGeneratorMethod.get());
|
eta, M.ms() - startTime.get(), currentGeneratorMethod.get());
|
||||||
|
|
||||||
if(cl.flip()) {
|
if (cl.flip()) {
|
||||||
Iris.info("Pregen: " + Form.f(generated.get()) + " of " + Form.f(totalChunks.get()) + " (" + Form.pc((double) generated.get() / (double) totalChunks.get(), 0) + ") " + Form.f((int) chunksPerSecond.getAverage()) + "/s ETA: " + Form.duration((double) eta, 2));
|
double percentage = ((double) generated.get() / (double) totalChunks.get()) * 100;
|
||||||
|
Iris.info("Pregen: " + Form.f(generated.get()) + " of " + Form.f(totalChunks.get()) + " (%.0f%%) " + Form.f((int) chunksPerSecond.getAverage()) + "/s ETA: " + Form.duration((double) eta, 2), percentage);
|
||||||
}
|
}
|
||||||
|
|
||||||
return 1000;
|
return 1000;
|
||||||
@@ -109,8 +111,12 @@ public class IrisPregenerator {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private long computeETA() {
|
private long computeETA() {
|
||||||
return (long) ((totalChunks.get() - generated.get()) *
|
return (long) (totalChunks.get() > 1024 ? // Generated chunks exceed 1/8th of total?
|
||||||
((double) (M.ms() - startTime.get()) / (double) generated.get()));
|
// If yes, use smooth function (which gets more accurate over time since its less sensitive to outliers)
|
||||||
|
((totalChunks.get() - generated.get()) * ((double) (M.ms() - startTime.get()) / (double) generated.get())) :
|
||||||
|
// If no, use quick function (which is less accurate over time but responds better to the initial delay)
|
||||||
|
((totalChunks.get() - generated.get()) / chunksPerSecond.getAverage()) * 1000 //
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void close() {
|
public void close() {
|
||||||
@@ -140,47 +146,58 @@ public class IrisPregenerator {
|
|||||||
generator.close();
|
generator.close();
|
||||||
ticker.interrupt();
|
ticker.interrupt();
|
||||||
listener.onClose();
|
listener.onClose();
|
||||||
|
getMantle().trim(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void visitRegion(int x, int z, boolean regions) {
|
private void visitRegion(int x, int z, boolean regions) {
|
||||||
while(paused.get() && !shutdown.get()) {
|
while (paused.get() && !shutdown.get()) {
|
||||||
J.sleep(50);
|
J.sleep(50);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(shutdown.get()) {
|
if (shutdown.get()) {
|
||||||
listener.onRegionSkipped(x, z);
|
listener.onRegionSkipped(x, z);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Position2 pos = new Position2(x, z);
|
Position2 pos = new Position2(x, z);
|
||||||
|
|
||||||
if(generatedRegions.contains(pos)) {
|
if (generatedRegions.contains(pos)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
currentGeneratorMethod.set(generator.getMethod(x, z));
|
currentGeneratorMethod.set(generator.getMethod(x, z));
|
||||||
boolean hit = false;
|
boolean hit = false;
|
||||||
if(generator.supportsRegions(x, z, listener) && regions) {
|
if (generator.supportsRegions(x, z, listener) && regions) {
|
||||||
hit = true;
|
hit = true;
|
||||||
listener.onRegionGenerating(x, z);
|
listener.onRegionGenerating(x, z);
|
||||||
generator.generateRegion(x, z, listener);
|
generator.generateRegion(x, z, listener);
|
||||||
} else if(!regions) {
|
} else if (!regions) {
|
||||||
hit = true;
|
hit = true;
|
||||||
listener.onRegionGenerating(x, z);
|
listener.onRegionGenerating(x, z);
|
||||||
PregenTask.iterateRegion(x, z, (xx, zz) -> generator.generateChunk(xx, zz, listener));
|
PregenTask.iterateRegion(x, z, (xx, zz) -> {
|
||||||
|
while (paused.get() && !shutdown.get()) {
|
||||||
|
J.sleep(50);
|
||||||
|
}
|
||||||
|
|
||||||
|
generator.generateChunk(xx, zz, listener);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
if(hit) {
|
if (hit) {
|
||||||
listener.onRegionGenerated(x, z);
|
listener.onRegionGenerated(x, z);
|
||||||
listener.onSaving();
|
|
||||||
generator.save();
|
if (saveLatch.flip()) {
|
||||||
|
listener.onSaving();
|
||||||
|
generator.save();
|
||||||
|
}
|
||||||
|
|
||||||
generatedRegions.add(pos);
|
generatedRegions.add(pos);
|
||||||
checkRegions();
|
checkRegions();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void checkRegion(int x, int z) {
|
private void checkRegion(int x, int z) {
|
||||||
if(generatedRegions.contains(new Position2(x, z))) {
|
if (generatedRegions.contains(new Position2(x, z))) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,163 @@
|
|||||||
|
package com.volmit.iris.core.pregenerator;
|
||||||
|
|
||||||
|
import com.google.gson.Gson;
|
||||||
|
import com.volmit.iris.Iris;
|
||||||
|
import com.volmit.iris.util.format.Form;
|
||||||
|
import com.volmit.iris.util.io.IO;
|
||||||
|
import com.volmit.iris.util.math.Position2;
|
||||||
|
import com.volmit.iris.util.math.Spiraler;
|
||||||
|
import com.volmit.iris.util.scheduling.ChronoLatch;
|
||||||
|
import com.volmit.iris.util.scheduling.J;
|
||||||
|
import io.papermc.lib.PaperLib;
|
||||||
|
import lombok.Builder;
|
||||||
|
import lombok.Data;
|
||||||
|
import org.bukkit.Bukkit;
|
||||||
|
import org.bukkit.World;
|
||||||
|
import org.bukkit.event.EventHandler;
|
||||||
|
import org.bukkit.event.Listener;
|
||||||
|
import org.bukkit.event.world.WorldUnloadEvent;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
|
|
||||||
|
public class LazyPregenerator extends Thread implements Listener {
|
||||||
|
private final LazyPregenJob job;
|
||||||
|
private final File destination;
|
||||||
|
private final int maxPosition;
|
||||||
|
private final World world;
|
||||||
|
private final long rate;
|
||||||
|
private final ChronoLatch latch;
|
||||||
|
|
||||||
|
public LazyPregenerator(LazyPregenJob job, File destination) {
|
||||||
|
this.job = job;
|
||||||
|
this.destination = destination;
|
||||||
|
this.maxPosition = new Spiraler(job.getRadiusBlocks() * 2, job.getRadiusBlocks() * 2, (x, z) -> {
|
||||||
|
}).count();
|
||||||
|
this.world = Bukkit.getWorld(job.getWorld());
|
||||||
|
this.rate = Math.round((1D / (job.chunksPerMinute / 60D)) * 1000D);
|
||||||
|
this.latch = new ChronoLatch(60000);
|
||||||
|
}
|
||||||
|
|
||||||
|
public LazyPregenerator(File file) throws IOException {
|
||||||
|
this(new Gson().fromJson(IO.readAll(file), LazyPregenJob.class), file);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void loadLazyGenerators() {
|
||||||
|
for (World i : Bukkit.getWorlds()) {
|
||||||
|
File lazygen = new File(i.getWorldFolder(), "lazygen.json");
|
||||||
|
|
||||||
|
if (lazygen.exists()) {
|
||||||
|
try {
|
||||||
|
LazyPregenerator p = new LazyPregenerator(lazygen);
|
||||||
|
p.start();
|
||||||
|
Iris.info("Started Lazy Pregenerator: " + p.job);
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@EventHandler
|
||||||
|
public void on(WorldUnloadEvent e) {
|
||||||
|
if (e.getWorld().equals(world)) {
|
||||||
|
interrupt();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void run() {
|
||||||
|
while (!interrupted()) {
|
||||||
|
J.sleep(rate);
|
||||||
|
tick();
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
saveNow();
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void tick() {
|
||||||
|
if (latch.flip()) {
|
||||||
|
save();
|
||||||
|
Iris.info("LazyGen: " + world.getName() + " RTT: " + Form.duration((Math.pow((job.radiusBlocks / 16D), 2) / job.chunksPerMinute) * 60 * 1000, 2));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (job.getPosition() >= maxPosition) {
|
||||||
|
if (job.isHealing()) {
|
||||||
|
int pos = (job.getHealingPosition() + 1) % maxPosition;
|
||||||
|
job.setHealingPosition(pos);
|
||||||
|
tickRegenerate(getChunk(pos));
|
||||||
|
} else {
|
||||||
|
Iris.verbose("Completed Lazy Gen!");
|
||||||
|
interrupt();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
int pos = job.getPosition() + 1;
|
||||||
|
job.setPosition(pos);
|
||||||
|
tickGenerate(getChunk(pos));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void tickGenerate(Position2 chunk) {
|
||||||
|
if (PaperLib.isPaper()) {
|
||||||
|
PaperLib.getChunkAtAsync(world, chunk.getX(), chunk.getZ(), true).thenAccept((i) -> Iris.verbose("Generated Async " + chunk));
|
||||||
|
} else {
|
||||||
|
J.s(() -> world.getChunkAt(chunk.getX(), chunk.getZ()));
|
||||||
|
Iris.verbose("Generated " + chunk);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void tickRegenerate(Position2 chunk) {
|
||||||
|
J.s(() -> world.regenerateChunk(chunk.getX(), chunk.getZ()));
|
||||||
|
Iris.verbose("Regenerated " + chunk);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Position2 getChunk(int position) {
|
||||||
|
int p = -1;
|
||||||
|
AtomicInteger xx = new AtomicInteger();
|
||||||
|
AtomicInteger zz = new AtomicInteger();
|
||||||
|
Spiraler s = new Spiraler(job.getRadiusBlocks() * 2, job.getRadiusBlocks() * 2, (x, z) -> {
|
||||||
|
xx.set(x);
|
||||||
|
zz.set(z);
|
||||||
|
});
|
||||||
|
|
||||||
|
while (s.hasNext() && p++ < position) {
|
||||||
|
s.next();
|
||||||
|
}
|
||||||
|
|
||||||
|
return new Position2(xx.get(), zz.get());
|
||||||
|
}
|
||||||
|
|
||||||
|
public void save() {
|
||||||
|
J.a(() -> {
|
||||||
|
try {
|
||||||
|
saveNow();
|
||||||
|
} catch (Throwable e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public void saveNow() throws IOException {
|
||||||
|
IO.writeAll(this.destination, new Gson().toJson(job));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Data
|
||||||
|
@Builder
|
||||||
|
public static class LazyPregenJob {
|
||||||
|
private String world;
|
||||||
|
@Builder.Default
|
||||||
|
private int healingPosition = 0;
|
||||||
|
@Builder.Default
|
||||||
|
private boolean healing = false;
|
||||||
|
@Builder.Default
|
||||||
|
private int chunksPerMinute = 32; // 48 hours is roughly 5000 radius
|
||||||
|
@Builder.Default
|
||||||
|
private int radiusBlocks = 5000;
|
||||||
|
@Builder.Default
|
||||||
|
private int position = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -43,13 +43,13 @@ public class PregenTask {
|
|||||||
private int height = 1;
|
private int height = 1;
|
||||||
|
|
||||||
public static void iterateRegion(int xr, int zr, Spiraled s, Position2 pull) {
|
public static void iterateRegion(int xr, int zr, Spiraled s, Position2 pull) {
|
||||||
for(Position2 i : ORDERS.computeIfAbsent(pull, PregenTask::computeOrder)) {
|
for (Position2 i : ORDERS.computeIfAbsent(pull, PregenTask::computeOrder)) {
|
||||||
s.on(i.getX() + (xr << 5), i.getZ() + (zr << 5));
|
s.on(i.getX() + (xr << 5), i.getZ() + (zr << 5));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void iterateRegion(int xr, int zr, Spiraled s) {
|
public static void iterateRegion(int xr, int zr, Spiraled s) {
|
||||||
iterateRegion(xr, zr, s, new Position2(0, 0));
|
iterateRegion(xr, zr, s, new Position2(-(xr << 5), -(zr << 5)));
|
||||||
}
|
}
|
||||||
|
|
||||||
private static KList<Position2> computeOrder(Position2 pull) {
|
private static KList<Position2> computeOrder(Position2 pull) {
|
||||||
@@ -57,7 +57,7 @@ public class PregenTask {
|
|||||||
new Spiraler(33, 33, (x, z) -> {
|
new Spiraler(33, 33, (x, z) -> {
|
||||||
int xx = (x + 15);
|
int xx = (x + 15);
|
||||||
int zz = (z + 15);
|
int zz = (z + 15);
|
||||||
if(xx < 0 || xx > 31 || zz < 0 || zz > 31) {
|
if (xx < 0 || xx > 31 || zz < 0 || zz > 31) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -74,7 +74,7 @@ public class PregenTask {
|
|||||||
new Spiraler(33, 33, (x, z) -> {
|
new Spiraler(33, 33, (x, z) -> {
|
||||||
int xx = x + 15;
|
int xx = x + 15;
|
||||||
int zz = z + 15;
|
int zz = z + 15;
|
||||||
if(xx < 0 || xx > 31 || zz < 0 || zz > 31) {
|
if (xx < 0 || xx > 31 || zz < 0 || zz > 31) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -86,11 +86,11 @@ public class PregenTask {
|
|||||||
|
|
||||||
public void iterateRegions(Spiraled s) {
|
public void iterateRegions(Spiraled s) {
|
||||||
new Spiraler(getWidth() * 2, getHeight() * 2, s)
|
new Spiraler(getWidth() * 2, getHeight() * 2, s)
|
||||||
.setOffset(center.getX(), center.getZ()).drain();
|
.setOffset(center.getX(), center.getZ()).drain();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void iterateAllChunks(Spiraled s) {
|
public void iterateAllChunks(Spiraled s) {
|
||||||
new Spiraler(getWidth() * 2, getHeight() * 2, (x, z) -> iterateRegion(x, z, s))
|
new Spiraler(getWidth() * 2, getHeight() * 2, (x, z) -> iterateRegion(x, z, s))
|
||||||
.setOffset(center.getX(), center.getZ()).drain();
|
.setOffset(center.getX(), center.getZ()).drain();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -43,10 +43,8 @@ public interface PregeneratorMethod {
|
|||||||
/**
|
/**
|
||||||
* Return true if regions can be generated
|
* Return true if regions can be generated
|
||||||
*
|
*
|
||||||
* @param x
|
* @param x the x region
|
||||||
* the x region
|
* @param z the z region
|
||||||
* @param z
|
|
||||||
* the z region
|
|
||||||
* @return true if they can be
|
* @return true if they can be
|
||||||
*/
|
*/
|
||||||
boolean supportsRegions(int x, int z, PregenListener listener);
|
boolean supportsRegions(int x, int z, PregenListener listener);
|
||||||
@@ -54,10 +52,8 @@ public interface PregeneratorMethod {
|
|||||||
/**
|
/**
|
||||||
* Return the name of the method being used
|
* Return the name of the method being used
|
||||||
*
|
*
|
||||||
* @param x
|
* @param x the x region
|
||||||
* the x region
|
* @param z the z region
|
||||||
* @param z
|
|
||||||
* the z region
|
|
||||||
* @return the name
|
* @return the name
|
||||||
*/
|
*/
|
||||||
String getMethod(int x, int z);
|
String getMethod(int x, int z);
|
||||||
@@ -66,22 +62,17 @@ public interface PregeneratorMethod {
|
|||||||
* Called to generate a region. Execute sync, if multicore internally, wait
|
* Called to generate a region. Execute sync, if multicore internally, wait
|
||||||
* for the task to complete
|
* for the task to complete
|
||||||
*
|
*
|
||||||
* @param x
|
* @param x the x
|
||||||
* the x
|
* @param z the z
|
||||||
* @param z
|
* @param listener signal chunks generating & generated. Parallel capable.
|
||||||
* the z
|
|
||||||
* @param listener
|
|
||||||
* signal chunks generating & generated. Parallel capable.
|
|
||||||
*/
|
*/
|
||||||
void generateRegion(int x, int z, PregenListener listener);
|
void generateRegion(int x, int z, PregenListener listener);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Called to generate a chunk. You can go async so long as save will wait on the threads to finish
|
* Called to generate a chunk. You can go async so long as save will wait on the threads to finish
|
||||||
*
|
*
|
||||||
* @param x
|
* @param x the x
|
||||||
* the x
|
* @param z the z
|
||||||
* @param z
|
|
||||||
* the z
|
|
||||||
*/
|
*/
|
||||||
void generateChunk(int x, int z, PregenListener listener);
|
void generateChunk(int x, int z, PregenListener listener);
|
||||||
|
|
||||||
|
|||||||
@@ -19,7 +19,6 @@
|
|||||||
package com.volmit.iris.core.pregenerator.methods;
|
package com.volmit.iris.core.pregenerator.methods;
|
||||||
|
|
||||||
import com.volmit.iris.Iris;
|
import com.volmit.iris.Iris;
|
||||||
import com.volmit.iris.core.IrisSettings;
|
|
||||||
import com.volmit.iris.core.pregenerator.PregenListener;
|
import com.volmit.iris.core.pregenerator.PregenListener;
|
||||||
import com.volmit.iris.core.pregenerator.PregeneratorMethod;
|
import com.volmit.iris.core.pregenerator.PregeneratorMethod;
|
||||||
import com.volmit.iris.core.tools.IrisToolbelt;
|
import com.volmit.iris.core.tools.IrisToolbelt;
|
||||||
@@ -31,6 +30,7 @@ import io.papermc.lib.PaperLib;
|
|||||||
import org.bukkit.Chunk;
|
import org.bukkit.Chunk;
|
||||||
import org.bukkit.World;
|
import org.bukkit.World;
|
||||||
|
|
||||||
|
import java.util.Objects;
|
||||||
import java.util.concurrent.Future;
|
import java.util.concurrent.Future;
|
||||||
|
|
||||||
public class AsyncPregenMethod implements PregeneratorMethod {
|
public class AsyncPregenMethod implements PregeneratorMethod {
|
||||||
@@ -39,7 +39,7 @@ public class AsyncPregenMethod implements PregeneratorMethod {
|
|||||||
private final KList<Future<?>> future;
|
private final KList<Future<?>> future;
|
||||||
|
|
||||||
public AsyncPregenMethod(World world, int threads) {
|
public AsyncPregenMethod(World world, int threads) {
|
||||||
if(!PaperLib.isPaper()) {
|
if (!PaperLib.isPaper()) {
|
||||||
throw new UnsupportedOperationException("Cannot use PaperAsync on non paper!");
|
throw new UnsupportedOperationException("Cannot use PaperAsync on non paper!");
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -51,42 +51,70 @@ public class AsyncPregenMethod implements PregeneratorMethod {
|
|||||||
private void unloadAndSaveAllChunks() {
|
private void unloadAndSaveAllChunks() {
|
||||||
try {
|
try {
|
||||||
J.sfut(() -> {
|
J.sfut(() -> {
|
||||||
if(world == null) {
|
if (world == null) {
|
||||||
Iris.warn("World was null somehow...");
|
Iris.warn("World was null somehow...");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
for(Chunk i : world.getLoadedChunks()) {
|
for (Chunk i : world.getLoadedChunks()) {
|
||||||
i.unload(true);
|
i.unload(true);
|
||||||
}
|
}
|
||||||
world.save();
|
world.save();
|
||||||
}).get();
|
}).get();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void completeChunk(int x, int z, PregenListener listener) {
|
private void completeChunk(int x, int z, PregenListener listener) {
|
||||||
try {
|
try {
|
||||||
PaperLib.getChunkAtAsync(world, x, z, true).get();
|
future.add(PaperLib.getChunkAtAsync(world, x, z, true).thenApply((i) -> {
|
||||||
listener.onChunkGenerated(x, z);
|
if (i == null) {
|
||||||
listener.onChunkCleaned(x, z);
|
|
||||||
} catch(Throwable e) {
|
}
|
||||||
|
|
||||||
|
listener.onChunkGenerated(x, z);
|
||||||
|
listener.onChunkCleaned(x, z);
|
||||||
|
return 0;
|
||||||
|
}));
|
||||||
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
J.sleep(5);
|
}
|
||||||
future.add(burst.complete(() -> completeChunk(x, z, listener)));
|
}
|
||||||
|
|
||||||
|
private void waitForChunksPartial(int maxWaiting) {
|
||||||
|
future.removeWhere(Objects::isNull);
|
||||||
|
|
||||||
|
while (future.size() > maxWaiting) {
|
||||||
|
try {
|
||||||
|
Future<?> i = future.remove(0);
|
||||||
|
|
||||||
|
if (i == null) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
i.get();
|
||||||
|
} catch (Throwable e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void waitForChunks() {
|
private void waitForChunks() {
|
||||||
for(Future<?> i : future.copy()) {
|
for (Future<?> i : future.copy()) {
|
||||||
|
if (i == null) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
i.get();
|
i.get();
|
||||||
future.remove(i);
|
future.remove(i);
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
future.removeWhere(Objects::isNull);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -107,7 +135,7 @@ public class AsyncPregenMethod implements PregeneratorMethod {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void save() {
|
public void save() {
|
||||||
waitForChunks();
|
waitForChunksPartial(256);
|
||||||
unloadAndSaveAllChunks();
|
unloadAndSaveAllChunks();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -123,17 +151,16 @@ public class AsyncPregenMethod implements PregeneratorMethod {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void generateChunk(int x, int z, PregenListener listener) {
|
public void generateChunk(int x, int z, PregenListener listener) {
|
||||||
if(future.size() > IrisSettings.getThreadCount(IrisSettings.get().getConcurrency().getParallelism())) { // TODO: FIX
|
|
||||||
waitForChunks();
|
|
||||||
}
|
|
||||||
|
|
||||||
listener.onChunkGenerating(x, z);
|
listener.onChunkGenerating(x, z);
|
||||||
|
if (future.size() > 256) {
|
||||||
|
waitForChunksPartial(256);
|
||||||
|
}
|
||||||
future.add(burst.complete(() -> completeChunk(x, z, listener)));
|
future.add(burst.complete(() -> completeChunk(x, z, listener)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Mantle getMantle() {
|
public Mantle getMantle() {
|
||||||
if(IrisToolbelt.isIrisWorld(world)) {
|
if (IrisToolbelt.isIrisWorld(world)) {
|
||||||
return IrisToolbelt.access(world).getEngine().getMantle().getMantle();
|
return IrisToolbelt.access(world).getEngine().getMantle().getMantle();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -18,17 +18,11 @@
|
|||||||
|
|
||||||
package com.volmit.iris.core.pregenerator.methods;
|
package com.volmit.iris.core.pregenerator.methods;
|
||||||
|
|
||||||
import com.volmit.iris.Iris;
|
|
||||||
import com.volmit.iris.core.IrisSettings;
|
|
||||||
import com.volmit.iris.core.pregenerator.PregenListener;
|
import com.volmit.iris.core.pregenerator.PregenListener;
|
||||||
import com.volmit.iris.core.pregenerator.PregeneratorMethod;
|
import com.volmit.iris.core.pregenerator.PregeneratorMethod;
|
||||||
import com.volmit.iris.core.tools.IrisToolbelt;
|
|
||||||
import com.volmit.iris.util.mantle.Mantle;
|
import com.volmit.iris.util.mantle.Mantle;
|
||||||
import com.volmit.iris.util.math.Position2;
|
|
||||||
import org.bukkit.World;
|
import org.bukkit.World;
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
|
|
||||||
public class HybridPregenMethod implements PregeneratorMethod {
|
public class HybridPregenMethod implements PregeneratorMethod {
|
||||||
private final PregeneratorMethod inWorld;
|
private final PregeneratorMethod inWorld;
|
||||||
private final World world;
|
private final World world;
|
||||||
@@ -60,7 +54,7 @@ public class HybridPregenMethod implements PregeneratorMethod {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean supportsRegions(int x, int z, PregenListener listener) {
|
public boolean supportsRegions(int x, int z, PregenListener listener) {
|
||||||
return inWorld.supportsRegions(x, z, listener);
|
return inWorld.supportsRegions(x, z, listener);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|||||||
@@ -40,10 +40,10 @@ public class MedievalPregenMethod implements PregeneratorMethod {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void waitForChunks() {
|
private void waitForChunks() {
|
||||||
for(CompletableFuture<?> i : futures) {
|
for (CompletableFuture<?> i : futures) {
|
||||||
try {
|
try {
|
||||||
i.get();
|
i.get();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -55,12 +55,12 @@ public class MedievalPregenMethod implements PregeneratorMethod {
|
|||||||
waitForChunks();
|
waitForChunks();
|
||||||
try {
|
try {
|
||||||
J.sfut(() -> {
|
J.sfut(() -> {
|
||||||
for(Chunk i : world.getLoadedChunks()) {
|
for (Chunk i : world.getLoadedChunks()) {
|
||||||
i.unload(true);
|
i.unload(true);
|
||||||
}
|
}
|
||||||
world.save();
|
world.save();
|
||||||
}).get();
|
}).get();
|
||||||
} catch(Throwable e) {
|
} catch (Throwable e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -97,7 +97,7 @@ public class MedievalPregenMethod implements PregeneratorMethod {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void generateChunk(int x, int z, PregenListener listener) {
|
public void generateChunk(int x, int z, PregenListener listener) {
|
||||||
if(futures.size() > IrisSettings.getThreadCount(IrisSettings.get().getConcurrency().getParallelism())) {
|
if (futures.size() > IrisSettings.getThreadCount(IrisSettings.get().getConcurrency().getParallelism())) {
|
||||||
waitForChunks();
|
waitForChunks();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -111,7 +111,7 @@ public class MedievalPregenMethod implements PregeneratorMethod {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Mantle getMantle() {
|
public Mantle getMantle() {
|
||||||
if(IrisToolbelt.isIrisWorld(world)) {
|
if (IrisToolbelt.isIrisWorld(world)) {
|
||||||
return IrisToolbelt.access(world).getEngine().getMantle().getMantle();
|
return IrisToolbelt.access(world).getEngine().getMantle().getMantle();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user