mirror of
https://github.com/curioustorvald/Terrarum.git
synced 2026-06-06 16:44:05 +09:00
Compare commits
833 Commits
the-flatte
...
inventory-
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e0fcf35f5b | ||
|
|
b2ad541355 | ||
|
|
eb2e47e2a5 | ||
|
|
b07e7f5fdd | ||
|
|
ac144da0b4 | ||
|
|
f5624af47c | ||
|
|
299e10a381 | ||
|
|
de164f6516 | ||
|
|
7f99bb4f4f | ||
|
|
619352e915 | ||
|
|
8469d22f93 | ||
|
|
c849669845 | ||
|
|
be6cddb1d6 | ||
|
|
2faebfcd27 | ||
|
|
64e9d3c0e4 | ||
|
|
4d46a44c51 | ||
|
|
87ce59194c | ||
|
|
4feb889aa8 | ||
|
|
f3e1cc53f8 | ||
|
|
37bc8a6aff | ||
|
|
04cf817303 | ||
|
|
f7ff220967 | ||
|
|
ccb9d33a36 | ||
|
|
096a34c6a6 | ||
|
|
4076e6d74e | ||
|
|
b5da05c9a0 | ||
|
|
25043cb36e | ||
|
|
1a98292b92 | ||
|
|
f469772c86 | ||
|
|
0bc52a7351 | ||
|
|
9670b5771f | ||
|
|
9e3008d6fe | ||
|
|
ae390fe6f5 | ||
|
|
02ad64487b | ||
|
|
8f08609d65 | ||
|
|
42b26597b4 | ||
|
|
9e082e914d | ||
|
|
a08d09b1b8 | ||
|
|
3982933aad | ||
|
|
ed5c823154 | ||
|
|
8589f1f8fa | ||
|
|
16f85f6bfa | ||
|
|
6b2970cbfd | ||
|
|
a501a353dd | ||
|
|
47d5d9c1b2 | ||
|
|
9ddfa48cd9 | ||
|
|
3b793d5ad4 | ||
|
|
82514180ea | ||
|
|
b31d5fcb89 | ||
|
|
aaba6976b3 | ||
|
|
facf29b34c | ||
|
|
19f0225e0d | ||
|
|
c629013a59 | ||
|
|
0d23d13401 | ||
|
|
90c8609f54 | ||
|
|
fa19d0ae51 | ||
|
|
4a177c5f76 | ||
|
|
fac45e8a97 | ||
|
|
e2195ba809 | ||
|
|
b4533b86df | ||
|
|
d4f349eda3 | ||
|
|
819eb612cd | ||
|
|
12b9ec3c06 | ||
|
|
d65305569c | ||
|
|
8b68e8917b | ||
|
|
7eee6e34d1 | ||
|
|
bf9f46756f | ||
|
|
3035887ff7 | ||
|
|
88fbe7a5c1 | ||
|
|
4a7b5952b0 | ||
|
|
42b87d30a0 | ||
|
|
54bbc473b1 | ||
|
|
c626c5b833 | ||
|
|
016f8ab554 | ||
|
|
c7251d1139 | ||
|
|
27af9ea7e0 | ||
|
|
3f58fcfb75 | ||
|
|
e7b0bf74e2 | ||
|
|
3e5a581e89 | ||
|
|
b319485637 | ||
|
|
5db5a23add | ||
|
|
c9904a113e | ||
|
|
0cf4264002 | ||
|
|
e4a512a420 | ||
|
|
fe3a27932c | ||
|
|
a0aed03af5 | ||
|
|
60df739563 | ||
|
|
385ea3b5a9 | ||
|
|
cfda47405d | ||
|
|
98993f1755 | ||
|
|
68ecb9139a | ||
|
|
ed8e35d593 | ||
|
|
3d59634ad9 | ||
|
|
fc15dd1f65 | ||
|
|
a31825dbce | ||
|
|
9972f80874 | ||
|
|
9a139be7ad | ||
|
|
612b7950ed | ||
|
|
86be4e4edb | ||
|
|
b051f7c1a1 | ||
|
|
5a0bf98737 | ||
|
|
240efc5537 | ||
|
|
278eff04b7 | ||
|
|
eea7ddffe0 | ||
|
|
47ff45bba3 | ||
|
|
33f74385bd | ||
|
|
17c9d184b2 | ||
|
|
77398abcb3 | ||
|
|
60e91b0532 | ||
|
|
951d9e0e71 | ||
|
|
02b67de91a | ||
|
|
ae59a179d8 | ||
|
|
9789f2ef55 | ||
|
|
9bf3bc103b | ||
|
|
b3db49c6e6 | ||
|
|
1cf62da4c5 | ||
|
|
bce3da1446 | ||
|
|
5e386eb9e9 | ||
|
|
98988d0065 | ||
|
|
e3a0bd6a5b | ||
|
|
bbcc457176 | ||
|
|
1e6c1eeeaf | ||
|
|
8973cd93fd | ||
|
|
d6040b6c17 | ||
|
|
79448a6f2b | ||
|
|
732e32b454 | ||
|
|
4a87e0a84a | ||
|
|
3fe514493b | ||
|
|
26d573c971 | ||
|
|
2b7376e1e4 | ||
|
|
debced982d | ||
|
|
1a1a9c52d3 | ||
|
|
fe97231db6 | ||
|
|
8a4bc98657 | ||
|
|
7b12f878dd | ||
|
|
56a9b186d6 | ||
|
|
6cced41888 | ||
|
|
b62412f2a8 | ||
|
|
8054ccf234 | ||
|
|
974c357d5e | ||
|
|
7077bf9fcf | ||
|
|
22916ebcec | ||
|
|
3fbf2754bd | ||
|
|
87f28435ee | ||
|
|
aaec9c6b5b | ||
|
|
df63824f69 | ||
|
|
3dfbde0e6c | ||
|
|
24569f53d6 | ||
|
|
d767dc1dbf | ||
|
|
d37f431144 | ||
|
|
8d58c09ffa | ||
|
|
bf2cc35d51 | ||
|
|
63d2880d8b | ||
|
|
b83da51e26 | ||
|
|
b37c782b4e | ||
|
|
801e737683 | ||
|
|
81625a4382 | ||
|
|
b6bc5d5246 | ||
|
|
edbbefe584 | ||
|
|
605b62b980 | ||
|
|
3e871a2e84 | ||
|
|
377fced95f | ||
|
|
29572f907e | ||
|
|
dd8404097b | ||
|
|
85985807e4 | ||
|
|
e628286442 | ||
|
|
53d970a179 | ||
|
|
c452be669b | ||
|
|
a399d22dd1 | ||
|
|
1a00f73d52 | ||
|
|
da1c752996 | ||
|
|
98ec8154d5 | ||
|
|
0396b026fb | ||
|
|
ce4b070428 | ||
|
|
fe61b65f0d | ||
|
|
bbf83b1944 | ||
|
|
4e89a32e4e | ||
|
|
601afc2636 | ||
|
|
88a288243c | ||
|
|
79b317d9e1 | ||
|
|
e5bf6874fd | ||
|
|
33c663d901 | ||
|
|
44e12825ac | ||
|
|
cf03e24af3 | ||
|
|
79d7c71000 | ||
|
|
af29e1b598 | ||
|
|
b16c23f1f0 | ||
|
|
9db6e86ac3 | ||
|
|
4f8c3591c2 | ||
|
|
a1d51d4028 | ||
|
|
593a528d32 | ||
|
|
4a99722f71 | ||
|
|
97f8aa6e6e | ||
|
|
85ab1b823d | ||
|
|
812e9e5b76 | ||
|
|
a87866438f | ||
|
|
c692928c1a | ||
|
|
5ff0c22b0f | ||
|
|
eb1273c561 | ||
|
|
50c110f34b | ||
|
|
c180953d7d | ||
|
|
a1ac9b177a | ||
|
|
c50d07b541 | ||
|
|
56fdb2f556 | ||
|
|
d2ddca85a6 | ||
|
|
9aa002f4cc | ||
|
|
3a5fcb9ba0 | ||
|
|
7d5a37cd6d | ||
|
|
75c79d8ca2 | ||
|
|
0b7a3a5636 | ||
|
|
c5e0de2393 | ||
|
|
19fb5b1319 | ||
|
|
2fff2c24cf | ||
|
|
92d5cac2ff | ||
|
|
471b0c805d | ||
|
|
16b7457d08 | ||
|
|
5c20ceeedc | ||
|
|
49df5f9676 | ||
|
|
48ba273317 | ||
|
|
52d6955ffc | ||
|
|
08f07e566d | ||
|
|
c423190725 | ||
|
|
61078cf5a8 | ||
|
|
eafdeddc94 | ||
|
|
9050378e81 | ||
|
|
fecb20da13 | ||
|
|
c89f602c06 | ||
|
|
21e14babb9 | ||
|
|
a4eac2173a | ||
|
|
c74fd0736a | ||
|
|
3ddf3ec123 | ||
|
|
1dcbd3ddbe | ||
|
|
c81414f097 | ||
|
|
bc2b1f68d1 | ||
|
|
e1340aac29 | ||
|
|
73b18e1252 | ||
|
|
bae9c60c81 | ||
|
|
7171055016 | ||
|
|
341c35fab7 | ||
|
|
e13c2ac59b | ||
|
|
80c29f871c | ||
|
|
2570b13ad4 | ||
|
|
4b91f485a5 | ||
|
|
9cf30ab3f4 | ||
|
|
63e416f472 | ||
|
|
464e0380e4 | ||
|
|
2942276341 | ||
|
|
d65f0cb17f | ||
|
|
ea69f28d05 | ||
|
|
3f213cfbe0 | ||
|
|
efa5d21717 | ||
|
|
3cc13f32c9 | ||
|
|
f3c2ddb3e2 | ||
|
|
58bbb73cb1 | ||
|
|
44745bfad1 | ||
|
|
5daea4fa57 | ||
|
|
98d013267e | ||
|
|
522279fec6 | ||
|
|
dfb9d0d8d9 | ||
|
|
8589847e3d | ||
|
|
4a9b003fe5 | ||
|
|
adcedaeba8 | ||
|
|
9922f81100 | ||
|
|
c69025a251 | ||
|
|
a66afb7b6a | ||
|
|
f12271f087 | ||
|
|
6afd36db64 | ||
|
|
7cbe09eee8 | ||
|
|
e56149f953 | ||
|
|
8ffdf5fbc5 | ||
|
|
a10d54c314 | ||
|
|
a54ba0925f | ||
|
|
bcb8db852c | ||
|
|
53737bd746 | ||
|
|
f24ddb5c82 | ||
|
|
391463a4e4 | ||
|
|
6dcdf32627 | ||
|
|
b55fe09d9f | ||
|
|
72ad6dc4e0 | ||
|
|
390dd51045 | ||
|
|
71baddd8bc | ||
|
|
ffb69813ed | ||
|
|
6c7e1c30c7 | ||
|
|
98c602ef65 | ||
|
|
439312e711 | ||
|
|
afa942e75d | ||
|
|
3148f18007 | ||
|
|
448e0aa9c5 | ||
|
|
7a62c06bc6 | ||
|
|
66fdb6ab5d | ||
|
|
f8d4d284d6 | ||
|
|
fcf9aa1b79 | ||
|
|
72dbc18128 | ||
|
|
33db76e3c8 | ||
|
|
9031ff0c2a | ||
|
|
b9fbacad14 | ||
|
|
21d7b83f96 | ||
|
|
10572f4d7e | ||
|
|
34364af1a1 | ||
|
|
003fed6cf0 | ||
|
|
589ac0de95 | ||
|
|
697449fca9 | ||
|
|
3da4719c8e | ||
|
|
3f7ce632cb | ||
|
|
5258c4b677 | ||
|
|
28cf447ec4 | ||
|
|
d1a84b17ab | ||
|
|
2a08f2c771 | ||
|
|
d16d232a0f | ||
|
|
1301943e6a | ||
|
|
5d8e64ca7f | ||
|
|
52b1bee3a3 | ||
|
|
a73a865d29 | ||
|
|
3f108a6ea9 | ||
|
|
a831a4d798 | ||
|
|
e3ed712a42 | ||
|
|
daf5c02605 | ||
|
|
e8b39fc668 | ||
|
|
c20d7edb34 | ||
|
|
28f305e76f | ||
|
|
4c3fc2352c | ||
|
|
01094d49eb | ||
|
|
7d3bf0eece | ||
|
|
75f128a8f7 | ||
|
|
514f1e9012 | ||
|
|
60db83eddb | ||
|
|
90a7fcd4d0 | ||
|
|
d93c6de851 | ||
|
|
f603b58307 | ||
|
|
074fe2438d | ||
|
|
69e9fa4b0f | ||
|
|
9373feff34 | ||
|
|
10c188bea7 | ||
|
|
cd1ad9277a | ||
|
|
465ed0d7a4 | ||
|
|
bd1c1bff8a | ||
|
|
8ac5f1dc9e | ||
|
|
268907ee9d | ||
|
|
9937c34d25 | ||
|
|
bdbb30bc58 | ||
|
|
bdbf6cd458 | ||
|
|
e4f456ffa7 | ||
|
|
73a6c844c8 | ||
|
|
84ca954a26 | ||
|
|
66b18bf8c5 | ||
|
|
6d0bff2879 | ||
|
|
14b485dc32 | ||
|
|
a192abd657 | ||
|
|
0d534fd60c | ||
|
|
a4dabbbf37 | ||
|
|
450874540c | ||
|
|
53c45d6829 | ||
|
|
1c839f7135 | ||
|
|
f133406df3 | ||
|
|
ae14026191 | ||
|
|
b9a4e0f64b | ||
|
|
aef601e9b8 | ||
|
|
88db71f780 | ||
|
|
ded9cb1a10 | ||
|
|
afba402c6c | ||
|
|
b027f662ce | ||
|
|
c60b0b42ad | ||
|
|
40580a57cd | ||
|
|
09b4a34d14 | ||
|
|
613b69a20f | ||
|
|
5738418f39 | ||
|
|
10cf3fb007 | ||
|
|
be20fd8328 | ||
|
|
d1a2e6b8f2 | ||
|
|
5bf8b6cad7 | ||
|
|
2c59d60a15 | ||
|
|
68df2a223e | ||
|
|
784a6a13e3 | ||
|
|
9040ff2c87 | ||
|
|
c4510f9c3b | ||
|
|
ebce90aa4b | ||
|
|
25d0e195c3 | ||
|
|
e209967730 | ||
|
|
f689e1de99 | ||
|
|
6e33dbdfaf | ||
|
|
b10e8aa777 | ||
|
|
6a343ae382 | ||
|
|
17b6738308 | ||
|
|
078cdfefa4 | ||
|
|
81f9c92e48 | ||
|
|
8237188dc3 | ||
|
|
7b120020e4 | ||
|
|
f4cd4f49b2 | ||
|
|
09b039c62f | ||
|
|
ff8791f48a | ||
|
|
43bc99548c | ||
|
|
380a14492f | ||
|
|
692e08fc1e | ||
|
|
33ad8520f8 | ||
|
|
9aa8eb395d | ||
|
|
34d50b8d70 | ||
|
|
07e8e21eae | ||
|
|
525273e37f | ||
|
|
34a8113d53 | ||
|
|
4f8cf2cb02 | ||
|
|
8a0abf22da | ||
|
|
9140d6d8b0 | ||
|
|
9133f05b5e | ||
|
|
790d16b85d | ||
|
|
adf60e357e | ||
|
|
f81db26e60 | ||
|
|
655eccbe19 | ||
|
|
5b31b4768f | ||
|
|
425cb82133 | ||
|
|
344e4ebdab | ||
|
|
32afb2e2e5 | ||
|
|
3100a093fd | ||
|
|
fb06200d26 | ||
|
|
1696cc8601 | ||
|
|
4072b9fb09 | ||
|
|
36160a6579 | ||
|
|
4986d570a0 | ||
|
|
1965eabaa3 | ||
|
|
90784afd48 | ||
|
|
258364f37e | ||
|
|
f99531c9d4 | ||
|
|
74cfc05fba | ||
|
|
15868a5a2d | ||
|
|
3abca8989a | ||
|
|
ae9a1ebcb4 | ||
|
|
18a05ace64 | ||
|
|
3b2c38cf0b | ||
|
|
6ecbb672fb | ||
|
|
30954d239a | ||
|
|
edd15a4f79 | ||
|
|
db110d1ca4 | ||
|
|
e3e97000a7 | ||
|
|
ce2d9a271a | ||
|
|
222aef7e3d | ||
|
|
08bbdaf70b | ||
|
|
7300b05442 | ||
|
|
cd13e04658 | ||
|
|
48de42d98b | ||
|
|
35c0c45500 | ||
|
|
6c01aa9b0b | ||
|
|
2335312081 | ||
|
|
abfd9b68fc | ||
|
|
500c72ebc9 | ||
|
|
00fc4f1b8c | ||
|
|
98755fab61 | ||
|
|
09d8702089 | ||
|
|
9080127d38 | ||
|
|
d7664c7f46 | ||
|
|
47da7d5b81 | ||
|
|
ef3690765d | ||
|
|
33c333e7fa | ||
|
|
10128a20a0 | ||
|
|
764945fc30 | ||
|
|
3098c0afd2 | ||
|
|
101c67a107 | ||
|
|
a1661fbb4e | ||
|
|
04c5e32ddf | ||
|
|
b78d488044 | ||
|
|
832e296bc5 | ||
|
|
46e5860143 | ||
|
|
4fa44abd3e | ||
|
|
191a91cb81 | ||
|
|
388d3d6f2f | ||
|
|
b1b29387e3 | ||
|
|
764edea832 | ||
|
|
16e4067d89 | ||
|
|
05a8f47006 | ||
|
|
1f1d6f1eda | ||
|
|
27f79238a1 | ||
|
|
6d553ea583 | ||
|
|
ad8d3ba210 | ||
|
|
e441cdf5f0 | ||
|
|
9c3c35067d | ||
|
|
7a60ae0629 | ||
|
|
258273fd25 | ||
|
|
dc502b2f12 | ||
|
|
803e59a0ee | ||
|
|
e31eaf0241 | ||
|
|
8181bec481 | ||
|
|
7c1d6e6b88 | ||
|
|
7e7e54eed7 | ||
|
|
57c9b7b277 | ||
|
|
984eb4de00 | ||
|
|
c4b4bfd2fc | ||
|
|
cf9bce5bac | ||
|
|
16a7d2abe7 | ||
|
|
a690b46456 | ||
|
|
b55cd415f2 | ||
|
|
4c2b73197d | ||
|
|
1c1ae37f41 | ||
|
|
57fa6de62a | ||
|
|
6f0a923df7 | ||
|
|
4b04bf3781 | ||
|
|
eca0469f32 | ||
|
|
d588f73ed6 | ||
|
|
b40a78b706 | ||
|
|
93a43899e7 | ||
|
|
155ba9eb56 | ||
|
|
4224d56b25 | ||
|
|
cc14218dd5 | ||
|
|
b856829ca9 | ||
|
|
4239bbe05b | ||
|
|
c43d2e6e68 | ||
|
|
a9bc4f47f8 | ||
|
|
1ce2d69809 | ||
|
|
bf9c172206 | ||
|
|
e966063e80 | ||
|
|
fa86ca2e05 | ||
|
|
8ef45968c2 | ||
|
|
9cc0a62188 | ||
|
|
df738348f6 | ||
|
|
f3b0044d5f | ||
|
|
3561ff9132 | ||
|
|
f5d36e2c92 | ||
|
|
0056f92b65 | ||
|
|
8da80e88a3 | ||
|
|
deaee71a44 | ||
|
|
f21ed3bf0d | ||
|
|
49966a53f6 | ||
|
|
4d0c772dd8 | ||
|
|
0123cc5b1a | ||
|
|
f4f0e59811 | ||
|
|
0695e3325d | ||
|
|
d9f576e4dc | ||
|
|
d830fa2873 | ||
|
|
091f79c7f8 | ||
|
|
a2f88ebbf1 | ||
|
|
8942f352a1 | ||
|
|
f721ad0db9 | ||
|
|
1aa90077a4 | ||
|
|
c6e9a46c3e | ||
|
|
3360ab0dfe | ||
|
|
4c3354f22c | ||
|
|
4eee5ee2b1 | ||
|
|
92091532e0 | ||
|
|
c7c68187eb | ||
|
|
81b65d57ca | ||
|
|
5c8cdd3162 | ||
|
|
ec871318a9 | ||
|
|
73d1a1bdc5 | ||
|
|
0e93f6609b | ||
|
|
ee3d98662c | ||
|
|
3612b55f97 | ||
|
|
d77b552518 | ||
|
|
e156349ec0 | ||
|
|
5f75288dc7 | ||
|
|
4658fa2aed | ||
|
|
74d76440ee | ||
|
|
630d6d2fed | ||
|
|
e072aff897 | ||
|
|
879583623d | ||
|
|
397b2a8795 | ||
|
|
5189c46ce5 | ||
|
|
ae1e99aa3e | ||
|
|
3735ce351e | ||
|
|
17e550a6a0 | ||
|
|
3045534222 | ||
|
|
292de8d56a | ||
|
|
434a2dbca3 | ||
|
|
626aa710c1 | ||
|
|
2239625efe | ||
|
|
78fc6fc657 | ||
|
|
76e8727bfc | ||
|
|
d2b7c76734 | ||
|
|
6fd2a4d69f | ||
|
|
4cfd3b8c45 | ||
|
|
197afc21ce | ||
|
|
e645eaade9 | ||
|
|
62edf9c3ae | ||
|
|
af34d94e6a | ||
|
|
c452017c84 | ||
|
|
98539e698f | ||
|
|
5367b97943 | ||
|
|
03b642ddd3 | ||
|
|
1b94d2ea14 | ||
|
|
967eafe8a3 | ||
|
|
d16e916502 | ||
|
|
69eb2d7a3b | ||
|
|
7069528714 | ||
|
|
6d4ac92133 | ||
|
|
79f3e8e28d | ||
|
|
b40af8e1b3 | ||
|
|
0658d95b12 | ||
|
|
c381250665 | ||
|
|
ad26b0f80c | ||
|
|
497a88c8de | ||
|
|
c953d84af9 | ||
|
|
0bad86bb9d | ||
|
|
809f1ad26f | ||
|
|
eee8a18875 | ||
|
|
932222a9c6 | ||
|
|
24b2e2a2af | ||
|
|
2d68fcd7c9 | ||
|
|
e48731b2e3 | ||
|
|
78e329d1c8 | ||
|
|
8f9022827c | ||
|
|
ab49846611 | ||
|
|
de19f49d26 | ||
|
|
1476ea737e | ||
|
|
9ade08013f | ||
|
|
305e992da6 | ||
|
|
6b929ac107 | ||
|
|
7a05931da8 | ||
|
|
108a3e6188 | ||
|
|
c1f829291a | ||
|
|
07681110c7 | ||
|
|
069eca7d9c | ||
|
|
abd1827182 | ||
|
|
872124429d | ||
|
|
9736d39e04 | ||
|
|
1ca3fff17e | ||
|
|
8daf0a2c38 | ||
|
|
d7c8b7f8f7 | ||
|
|
6bbfd5d167 | ||
|
|
baf2a47d75 | ||
|
|
4664c9ba0d | ||
|
|
33c326febe | ||
|
|
fded7f1dfb | ||
|
|
da796194d6 | ||
|
|
d11fd281f4 | ||
|
|
85dac4a109 | ||
|
|
40423ede52 | ||
|
|
2701934f89 | ||
|
|
941d9fa107 | ||
|
|
c8debd351f | ||
|
|
c5fa83b2f4 | ||
|
|
24a6aa5a9a | ||
|
|
51a2e47430 | ||
|
|
f3075dfc18 | ||
|
|
6715308f88 | ||
|
|
6901b17bb6 | ||
|
|
35f2cf6b4d | ||
|
|
d9258bcb84 | ||
|
|
f45a3d252a | ||
|
|
b5e908d271 | ||
|
|
ade77473c4 | ||
|
|
60d1a5cea2 | ||
|
|
7cd7b4047f | ||
|
|
a22d2dbb92 | ||
|
|
f5636fe0d3 | ||
|
|
b892d2e70c | ||
|
|
948f922041 | ||
|
|
cec6d9c3c2 | ||
|
|
6c72bef0de | ||
|
|
0266f518fc | ||
|
|
fe21340186 | ||
|
|
f72f18a821 | ||
|
|
516314c47f | ||
|
|
c2ac328cab | ||
|
|
55cdac9269 | ||
|
|
07d609ca72 | ||
|
|
a506269906 | ||
|
|
af027e616d | ||
|
|
77b563396e | ||
|
|
04161525eb | ||
|
|
98a67c80c6 | ||
|
|
0023b4a4a8 | ||
|
|
a8398765c6 | ||
|
|
a5d0d5e525 | ||
|
|
6df79b96dd | ||
|
|
5b8bee6777 | ||
|
|
83b9f74100 | ||
|
|
76260cbc18 | ||
|
|
d9a01a70c3 | ||
|
|
a7849d2635 | ||
|
|
06949848f8 | ||
|
|
595681d6e9 | ||
|
|
0e1c46f18d | ||
|
|
3505b38789 | ||
|
|
fe8163c1e4 | ||
|
|
42efbd5297 | ||
|
|
e3ac877c3d | ||
|
|
3569e3ccbf | ||
|
|
b560011d2f | ||
|
|
e31640cba6 | ||
|
|
e76458bff6 | ||
|
|
9645b28674 | ||
|
|
558430b4f3 | ||
|
|
e9f8f47e20 | ||
|
|
1149311076 | ||
|
|
d3b54ae300 | ||
|
|
ef176909b4 | ||
|
|
553816e8c4 | ||
|
|
1d8e66a9cc | ||
|
|
772436b16b | ||
|
|
cdf961df09 | ||
|
|
f6c5d22dc2 | ||
|
|
01a32ad00c | ||
|
|
dcd21bc3fa | ||
|
|
7ffb417618 | ||
|
|
b05706a7c5 | ||
|
|
82ddfeb6ee | ||
|
|
59270f2c40 | ||
|
|
e67b97257c | ||
|
|
636b0ffe4f | ||
|
|
e6e962ecf7 | ||
|
|
81c031966c | ||
|
|
749a82bcf7 | ||
|
|
b040531f99 | ||
|
|
f9897bc439 | ||
|
|
ff434b45fc | ||
|
|
1c6560797d | ||
|
|
ff95f9e402 | ||
|
|
75192bef17 | ||
|
|
bdff19237e | ||
|
|
05560cf04c | ||
|
|
5d03bb96f3 | ||
|
|
ee7d51c21b | ||
|
|
6ce45abfc4 | ||
|
|
2928aa2eb7 | ||
|
|
c94418e98f | ||
|
|
d0702c9159 | ||
|
|
1be8e5d0c7 | ||
|
|
2bf9acb07a | ||
|
|
388e4675f4 | ||
|
|
25ce7958ae | ||
|
|
ad60b21d2a | ||
|
|
64f36d2d7c | ||
|
|
93b18dfb18 | ||
|
|
65bc67710c | ||
|
|
f1afb67c77 | ||
|
|
86d3a4a08d | ||
|
|
9731c8384a | ||
|
|
33da9777ea | ||
|
|
33657624a6 | ||
|
|
07ee987411 | ||
|
|
3578df4770 | ||
|
|
72b7adcf39 | ||
|
|
0fe3e7949b | ||
|
|
c595270faa | ||
|
|
d421d7964b | ||
|
|
d753365e54 | ||
|
|
b6c3467fe1 | ||
|
|
116b4cc390 | ||
|
|
f912b33f09 | ||
|
|
a5dd5b9e98 | ||
|
|
4087a93142 | ||
|
|
f51417e709 | ||
|
|
cf9414f2df | ||
|
|
fd7d724f39 | ||
|
|
329beb3197 | ||
|
|
528fdc9fc5 | ||
|
|
81f0499c9d | ||
|
|
33a774b5b7 | ||
|
|
3727a9d27f | ||
|
|
58205e5eb5 | ||
|
|
2f75e276b2 | ||
|
|
31b7203d01 | ||
|
|
5a0b3c6eb1 | ||
|
|
c9932fc81b | ||
|
|
dad876308c | ||
|
|
145a4e5e71 | ||
|
|
98409f09c0 | ||
|
|
81529eb215 | ||
|
|
b9c93dd6b0 | ||
|
|
057df6632a | ||
|
|
81acfecbd7 | ||
|
|
5499ded796 | ||
|
|
1002f910e4 | ||
|
|
61427b849a | ||
|
|
eff1cb1e62 | ||
|
|
a53f818ba6 | ||
|
|
70236f42ff | ||
|
|
d9a3318768 | ||
|
|
9a935c2e15 | ||
|
|
d241e5cbb0 | ||
|
|
8438714062 | ||
|
|
49a9278c59 | ||
|
|
fcdac4b759 | ||
|
|
fc9516fd39 | ||
|
|
e74a738274 | ||
|
|
6bff02d91e | ||
|
|
86fad6390f | ||
|
|
bad6ff296a | ||
|
|
7fc2d85c46 | ||
|
|
1e9c04d7c0 | ||
|
|
e01ad32849 | ||
|
|
3ffdd7233f | ||
|
|
06cab5effc | ||
|
|
5a5fb45c3b | ||
|
|
c96fb5e017 | ||
|
|
1a33c3be5a | ||
|
|
b3a355f51d | ||
|
|
0ad7db3b51 | ||
|
|
b57b0cb04c | ||
|
|
8504337da9 | ||
|
|
f71905b880 | ||
|
|
f2f5cd7daf | ||
|
|
235f774ff6 | ||
|
|
464d30a384 | ||
|
|
3b99546f33 | ||
|
|
009b55481b | ||
|
|
19a094b2fa | ||
|
|
72e7931f4d | ||
|
|
3eadb6b5e5 | ||
|
|
0e4dd79cc1 | ||
|
|
1ca162f72e | ||
|
|
f676938176 | ||
|
|
28b67ec68b | ||
|
|
8a759cb178 | ||
|
|
c7add8f0a8 | ||
|
|
66e4dcd1c4 | ||
|
|
d707287754 | ||
|
|
d9381fc58e | ||
|
|
cf6e268ff6 | ||
|
|
039ccea58f | ||
|
|
bba2f3ce20 | ||
|
|
b592b8fa0f | ||
|
|
2ac7efeaac | ||
|
|
b82d172d58 | ||
|
|
fbe02ab19c | ||
|
|
41f9f4032d | ||
|
|
7ca4d03cf8 | ||
|
|
7b2b6caf82 | ||
|
|
924c7db5eb | ||
|
|
b7fb8ff4da | ||
|
|
6b37b2b9d6 | ||
|
|
2ea3ce0c67 | ||
|
|
b04d062935 | ||
|
|
9b32cf63ff | ||
|
|
d357ef0245 | ||
|
|
2129cce7f3 | ||
|
|
3b24ce306f | ||
|
|
c8c1bdf836 | ||
|
|
7f5760f84e | ||
|
|
4a54c87826 | ||
|
|
e2da14da8a | ||
|
|
7248616e58 | ||
|
|
54c643b35e | ||
|
|
33b5a21c26 | ||
|
|
5ad34b96ac | ||
|
|
1095cb451f | ||
|
|
62ff6e9ded |
3
.gitattributes
vendored
3
.gitattributes
vendored
@@ -5,5 +5,4 @@
|
||||
*.opus filter=lfs diff=lfs merge=lfs -text
|
||||
*.pdf filter=lfs diff=lfs merge=lfs -text
|
||||
*.zip filter=lfs diff=lfs merge=lfs -text
|
||||
*.kra filter=lfs diff=lfs merge=lfs -text
|
||||
*.png filter=lfs diff=lfs merge=lfs -text
|
||||
*.kra filter=lfs diff=lfs merge=lfs -text
|
||||
@@ -1,6 +1,6 @@
|
||||
*Terrarum*
|
||||
|
||||
Copyright (C) 2013-2021 Minjae Song ("CuriousTorvald")
|
||||
Copyright (C) 2013-2020 Minjaesong (Torvald)
|
||||
|
||||
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
|
||||
@@ -19,7 +19,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
*Terrarum Sans Bitmap*
|
||||
|
||||
Copyright (c) 2017-2020 Minjae Song ("CuriousTorvald") and the contributors
|
||||
Copyright (c) 2017-2019 Minjae Song (Torvald) and the contributors
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -113,7 +113,7 @@ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
|
||||
OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
Kotlin translated and modified code Copyright (C) 2016 Minjae Song ("CuriousTorvald")
|
||||
Kotlin translated and modified code Copyright (C) 2016 Minjaesong (Torvald)
|
||||
|
||||
----
|
||||
|
||||
|
||||
@@ -1,42 +1,17 @@
|
||||
## Prefix-ID Referencing
|
||||
|
||||
Every blocks and items have Prefix-ID Referencing scheme, which is defined as follows:
|
||||
|
||||
```<Prefix>@<Modname>:<Integer ID>```
|
||||
|
||||
where Prefix is predefined (see below), Integer ID is arbitrarily chosen within a domain.
|
||||
|
||||
### Prefixes
|
||||
|Name|Description|
|
||||
|----|-----------|
|
||||
|wall|Wall, only used by the Inventory to differentiate walls from blocks (therefore wall shares same "ID Space" with blocks/fluids/wires)|
|
||||
|item|Item (Static), uses different "ID Space" with blocks/walls/fluids/wires|
|
||||
|
||||
Notes:
|
||||
- BlockCodex and ItemCodex will not store prefix part of the ID, as blocks and walls are identical in properties
|
||||
- Wires and Fluids use the same "ID Space" as the tiles; they just happened to exclusive to their own layers.
|
||||
This simplifies many things e.g. only one TileID-to-AtlasTileNumber map is needed and the renderer will
|
||||
greatly benefit from it.
|
||||
|
||||
### Predefined Modnames
|
||||
|
||||
|Name|Description|
|
||||
|----|-----------|
|
||||
|dyn|Dynamic Item|
|
||||
|actor|Actor As an Item. Integer ID is identical to the actor's Reference ID|
|
||||
|virt|Virtual Tile Number|
|
||||
|
||||
### Integer ID Domains
|
||||
|
||||
|Range|Description|
|
||||
|-----|-----------|
|
||||
|1..2147483647|Integer ID for dynamic items|
|
||||
|0x1000_0000..0x7FFF_FFFF|Reference ID for Actors (1879M possible)|
|
||||
|1..2147483647|Integer ID for virtual tiles|
|
||||
|0..4095|Tiles (4096 possible)|
|
||||
|4096..8191|Walls (4096 possible)|
|
||||
|8192..8447|Wires (256 possible)|
|
||||
|8448..0x0F_FFFF|Items (static) (1M possible)|
|
||||
|0x10_0000..0x0FFF_FFFF|Items (dynamic\*) (267M possible)|
|
||||
|0x1000_0000..0x7FFF_FFFF|Actors (1879M possible)|
|
||||
|-1..-65536|Virtual Tiles|
|
||||
|-2147483648..-65537 (all negative numbers)|Faction (2147M possible)|
|
||||
|
||||
* dynamic items have own properties that will persist through savegame.
|
||||
|
||||
Actor range in-depth
|
||||
Actors range in-depth
|
||||
|
||||
|Range|Description|
|
||||
|-----|-----------|
|
||||
|
||||
BIN
assets/32opus_poke.ogg
LFS
Normal file
BIN
assets/32opus_poke.ogg
LFS
Normal file
Binary file not shown.
BIN
assets/graphics/blocks/init.tga
LFS
BIN
assets/graphics/blocks/init.tga
LFS
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -1,5 +1,6 @@
|
||||
"id";"drop";"name";"shdr";"shdg";"shdb";"shduv";"str";"dsty";"mate";"solid";"plat";"wall";"grav";"dlfn";"fv";"fr";"lumr";"lumg";"lumb";"lumuv";"colour";"vscs"
|
||||
"0";"0";"BLOCK_AIR";"0.0312";"0.0312";"0.0312";"0.0312";"1";"1";"NULL";"0";"0";"1";"N/A";"0";"0";"4";"0.0000";"0.0000";"0.0000";"0.0000";"N/A";"N/A"
|
||||
"1";"1";"BLOCK_MIASMA";"0.0312";"0.0312";"0.0312";"0.0312";"1";"1";"NULL";"0";"0";"1";"N/A";"0";"0";"4";"0.0000";"0.0000";"0.0000";"0.0000";"N/A";"N/A"
|
||||
"16";"17";"BLOCK_STONE";"0.1252";"0.1252";"0.1252";"0.1252";"48";"2400";"ROCK";"1";"0";"1";"N/A";"0";"4";"16";"0.0000";"0.0000";"0.0000";"0.0000";"N/A";"N/A"
|
||||
"17";"17";"BLOCK_STONE_QUARRIED";"0.1252";"0.1252";"0.1252";"0.1252";"48";"2400";"ROCK";"1";"0";"1";"N/A";"0";"4";"16";"0.0000";"0.0000";"0.0000";"0.0000";"N/A";"N/A"
|
||||
"18";"18";"BLOCK_STONE_TILE_WHITE";"0.1252";"0.1252";"0.1252";"0.1252";"48";"2400";"ROCK";"1";"0";"1";"N/A";"0";"4";"16";"0.0000";"0.0000";"0.0000";"0.0000";"N/A";"N/A"
|
||||
@@ -106,8 +107,8 @@
|
||||
"4093";"0";"ACTORBLOCK_ALLOW_MOVE_DOWN";"0.0312";"0.0312";"0.0312";"0.0312";"1";"1";"NULL";"0";"1";"0";"N/A";"0";"0";"0";"0.0";"0.0";"0.0";"0.0";"N/A";"N/A"
|
||||
"4094";"0";"ACTORBLOCK_NO_PASS_RIGHT";"0.0312";"0.0312";"0.0312";"0.0312";"1";"1";"NULL";"0";"0";"0";"N/A";"0";"0";"0";"0.0";"0.0";"0.0";"0.0";"N/A";"N/A"
|
||||
"4095";"0";"ACTORBLOCK_NO_PASS_LEFT";"0.0312";"0.0312";"0.0312";"0.0312";"1";"1";"NULL";"0";"0";"0";"N/A";"0";"0";"0";"0.0";"0.0";"0.0";"0.0";"N/A";"N/A"
|
||||
"65536";"0";"BLOCK_WATER";"0.1016";"0.0744";"0.0508";"0.0826";"100";"1000";"WATR";"0";"0";"0";"0";"0";"0";"16";"0.0000";"0.0000";"0.0000";"0.0000";"005599A6";"16"
|
||||
"65537";"0";"BLOCK_LAVA";"0.9696";"0.9696";"0.9696";"0.9696";"100";"2600";"ROCK";"0";"0";"0";"0";"0";"0";"16";"0.7664";"0.2032";"0.0000";"0.0000";"FF4600E6";"32"
|
||||
"4096";"0";"BLOCK_WATER";"0.1016";"0.0744";"0.0508";"0.0826";"100";"1000";"WATR";"0";"0";"0";"0";"0";"0";"16";"0.0000";"0.0000";"0.0000";"0.0000";"005599A6";"16"
|
||||
"4097";"0";"BLOCK_LAVA";"0.9696";"0.9696";"0.9696";"0.9696";"100";"2600";"ROCK";"0";"0";"0";"0";"0";"0";"16";"0.7664";"0.2032";"0.0000";"0.0000";"FF4600E6";"32"
|
||||
"-1";"0";"BLOCK_NULL";"4.0000";"4.0000";"4.0000";"4.0000";"-1";"2600";"NULL";"0";"0";"1";"N/A";"0";"0";"16";"0.0000";"0.0000";"0.0000";"0.0000";"N/A";"N/A"
|
||||
|
||||
|
||||
|
||||
|
@@ -1,12 +0,0 @@
|
||||
"id";"drop";"name";"accept";"inputcount";"inputtype";"outputtype"
|
||||
"8192";"8192";"WIRE_RED";"digital_bit";"N/A";"N/A";"N/A"
|
||||
"8193";"8193";"WIRE_GREEN";"digital_bit";"N/A";"N/A";"N/A"
|
||||
"8194";"8194";"WIRE_BLUE";"digital_bit";"N/A";"N/A";"N/A"
|
||||
"8195";"8195";"WIRE_BUNDLE";"digital_3bits";"N/A";"N/A";"N/A"
|
||||
"bundlemaker";"bundlemaker";"WIRE_BUNDLEMAKER";"N/A";3;"digital_bit";"digital_3bits"
|
||||
|
||||
|
||||
# accept: which wiretype (defined elsewhere) the wires acceps. Use comma to separate multiple. N/A for electronic components (aka "not wires")
|
||||
# inputcount: how many sides are input (outputcount is deduced from the inputcount). N/A for wires
|
||||
# inputtype: which wiretype it accepts. N/A for wires
|
||||
# outputtype: which wiretype it emits. N/A for wires
|
||||
|
Can't render this file because it contains an unexpected character in line 9 and column 131.
|
@@ -1,7 +1,7 @@
|
||||
"id";"classname"
|
||||
"1";"net.torvald.terrarum.modulebasegame.gameitems.PickaxeCopper"
|
||||
"2";"net.torvald.terrarum.modulebasegame.gameitems.PickaxeIron"
|
||||
"3";"net.torvald.terrarum.modulebasegame.gameitems.PickaxeSteel"
|
||||
"4";"net.torvald.terrarum.modulebasegame.gameitems.WirePieceSignalWire"
|
||||
"5";"net.torvald.terrarum.modulebasegame.gameitems.TikiTorchTester"
|
||||
"6";"net.torvald.terrarum.modulebasegame.gameitems.ItemCraftingTable"
|
||||
"id";"classname"
|
||||
"8448";"net.torvald.terrarum.modulebasegame.gameitems.PickaxeCopper"
|
||||
"8449";"net.torvald.terrarum.modulebasegame.gameitems.PickaxeIron"
|
||||
"8450";"net.torvald.terrarum.modulebasegame.gameitems.PickaxeSteel"
|
||||
"8466";"net.torvald.terrarum.modulebasegame.gameitems.WirePieceSignalWire"
|
||||
"8467";"net.torvald.terrarum.modulebasegame.gameitems.TikiTorchTester"
|
||||
"8468";"net.torvald.terrarum.modulebasegame.gameitems.ItemCraftingTable"
|
||||
|
||||
|
@@ -76,7 +76,7 @@ void main() {
|
||||
int tile = getTileFromColor(tileFromMap);
|
||||
int breakage = getBreakageFromColor(tileFromMap);
|
||||
ivec2 tileXY = getTileXY(tile);
|
||||
ivec2 breakageXY = getTileXY(breakage + 5); // +5 is hard-coded constant that depends on the contents of the atlas
|
||||
ivec2 breakageXY = getTileXY(breakage + 5); // +5 is hard-coded constant that depends on the atlas
|
||||
|
||||
// calculate the UV coord value for texture sampling //
|
||||
|
||||
|
||||
@@ -1,32 +1,32 @@
|
||||
{
|
||||
"displayfps": 0,
|
||||
"usevsync": false,
|
||||
"screenwidth": 1280,
|
||||
"screenheight": 720,
|
||||
"screenwidth": 1110,
|
||||
"screenheight": 740,
|
||||
"language": "enUS",
|
||||
"notificationshowuptime": 4000,
|
||||
"multithread": true,
|
||||
"multithreadedlight": false,
|
||||
"showhealthmessageonstartup": true,
|
||||
"usexinput": true,
|
||||
"config_gamepadkeyn": 3,
|
||||
"config_gamepadkeyw": 2,
|
||||
"config_gamepadkeys": 0,
|
||||
"config_gamepadkeye": 1,
|
||||
"config_gamepadlup": 4,
|
||||
"config_gamepadrup": 5,
|
||||
"config_gamepadselect": 6,
|
||||
"config_gamepadstart": 7,
|
||||
"config_gamepadltrigger": 8,
|
||||
"config_gamepadrtrigger": 9,
|
||||
"config_gamepadlthumb": 10,
|
||||
"config_gamepadrthumb": 11,
|
||||
"config_gamepadaxislx": 1,
|
||||
"config_gamepadaxisly": 0,
|
||||
"config_gamepadaxisrx": 3,
|
||||
"config_gamepadaxisry": 2,
|
||||
"config_gamepadtriggeraxis": 4,
|
||||
"config_gamepadtriggeraxis2": 5,
|
||||
"gamepadkeyn": 3,
|
||||
"gamepadkeyw": 2,
|
||||
"gamepadkeys": 0,
|
||||
"gamepadkeye": 1,
|
||||
"gamepadlup": 4,
|
||||
"gamepadrup": 5,
|
||||
"gamepadselect": 6,
|
||||
"gamepadstart": 7,
|
||||
"gamepadltrigger": 8,
|
||||
"gamepadrtrigger": 9,
|
||||
"gamepadlthumb": 10,
|
||||
"gamepadrthumb": 11,
|
||||
"gamepadaxislx": 1,
|
||||
"gamepadaxisly": 0,
|
||||
"gamepadaxisrx": 3,
|
||||
"gamepadaxisry": 2,
|
||||
"gamepadtriggeraxis": 4,
|
||||
"gamepadtriggeraxis2": 5,
|
||||
"gamepadaxiszeropoints": [
|
||||
-0.011,
|
||||
-0.022,
|
||||
@@ -34,24 +34,24 @@
|
||||
-0.044
|
||||
],
|
||||
"gamepadlabelstyle": "msxbone",
|
||||
"config_keyup":34,
|
||||
"config_keyleft":46,
|
||||
"config_keydown":47,
|
||||
"config_keyright":48,
|
||||
"config_keyinventory":45,
|
||||
"config_keyinteract":44,
|
||||
"config_keymovementaux": 29,
|
||||
"config_keyclose": 31,
|
||||
"config_keyzoom": 54,
|
||||
"config_keygamemenu": 61,
|
||||
"config_keyquicksel": 59,
|
||||
"config_keyquickselalt": [
|
||||
"keyup":34,
|
||||
"keyleft":46,
|
||||
"keydown":47,
|
||||
"keyright":48,
|
||||
"keyinventory":45,
|
||||
"keyinteract":44,
|
||||
"keymovementaux": 29,
|
||||
"keyclose": 31,
|
||||
"keyzoom": 54,
|
||||
"keygamemenu": 61,
|
||||
"keyquicksel": 59,
|
||||
"keyquickselalt": [
|
||||
67,
|
||||
129,
|
||||
73
|
||||
],
|
||||
"config_keyjump": 62,
|
||||
"config_keyquickslots": [
|
||||
"keyjump": 62,
|
||||
"keyquickslots": [
|
||||
8,
|
||||
9,
|
||||
10,
|
||||
@@ -63,8 +63,8 @@
|
||||
16,
|
||||
7
|
||||
],
|
||||
"config_mouseprimary": 0,
|
||||
"config_mousesecondary": 1,
|
||||
"mouseprimary": 0,
|
||||
"mousesecondary": 1,
|
||||
"pcgamepadenv": "console",
|
||||
"maxparticles": 768,
|
||||
"temperatureunit": 1,
|
||||
|
||||
Binary file not shown.
@@ -11,9 +11,6 @@ import sun.misc.Unsafe
|
||||
*/
|
||||
|
||||
internal object UnsafeHelper {
|
||||
var unsafeAllocatedSize = 0L
|
||||
internal set
|
||||
|
||||
val unsafe: Unsafe
|
||||
|
||||
init {
|
||||
@@ -47,7 +44,7 @@ internal object UnsafeHelper {
|
||||
*
|
||||
* @return offset from the array's base memory address (aka pointer) that the actual data begins.
|
||||
*/
|
||||
fun getArrayOffset(obj: Any) = unsafe.arrayBaseOffset(obj.javaClass).toLong()
|
||||
fun getArrayOffset(obj: Any) = unsafe.arrayBaseOffset(obj.javaClass)
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -60,10 +57,6 @@ internal object UnsafeHelper {
|
||||
* Use of hashCode() is forbidden, use the pointer instead.
|
||||
*/
|
||||
internal class UnsafePtr(pointer: Long, allocSize: Long) {
|
||||
init {
|
||||
UnsafeHelper.unsafeAllocatedSize += allocSize
|
||||
}
|
||||
|
||||
var destroyed = false
|
||||
private set
|
||||
|
||||
@@ -74,10 +67,8 @@ internal class UnsafePtr(pointer: Long, allocSize: Long) {
|
||||
private set
|
||||
|
||||
fun realloc(newSize: Long) {
|
||||
UnsafeHelper.unsafeAllocatedSize -= size
|
||||
ptr = UnsafeHelper.unsafe.reallocateMemory(ptr, newSize)
|
||||
size = newSize
|
||||
UnsafeHelper.unsafeAllocatedSize += size
|
||||
}
|
||||
|
||||
fun destroy() {
|
||||
@@ -88,17 +79,16 @@ internal class UnsafePtr(pointer: Long, allocSize: Long) {
|
||||
printStackTrace(this)
|
||||
|
||||
destroyed = true
|
||||
|
||||
UnsafeHelper.unsafeAllocatedSize -= size
|
||||
}
|
||||
}
|
||||
|
||||
private inline fun checkNullPtr(index: Long) { // ignore what IDEA says and do inline this
|
||||
//// commenting out because of the suspected (or minor?) performance impact.
|
||||
//// You may break the glass and use this tool when some fucking incomprehensible bugs ("vittujen vitun bugit")
|
||||
//// appear (e.g. getting garbage values when it fucking shouldn't)
|
||||
// commenting out because of the suspected (or minor?) performance impact.
|
||||
// You may break the glass and use this tool when some fucking incomprehensible bugs ("vittujen vitun bugit")
|
||||
// appear (e.g. getting garbage values when it fucking shouldn't)
|
||||
assert(!destroyed) { throw NullPointerException("The pointer is already destroyed ($this)") }
|
||||
|
||||
//assert(!destroyed) { throw NullPointerException("The pointer is already destroyed ($this)") }
|
||||
// OOB Check: debugging purposes only -- comment out for the production
|
||||
//if (index !in 0 until size) throw IndexOutOfBoundsException("Index: $index; alloc size: $size")
|
||||
}
|
||||
|
||||
|
||||
@@ -34,10 +34,10 @@ import com.badlogic.gdx.utils.NumberUtils
|
||||
class Cvec {
|
||||
|
||||
/** the red, green, blue and alpha components */
|
||||
var r: Float = 0f
|
||||
var g: Float = 0f
|
||||
var b: Float = 0f
|
||||
var a: Float = 0f
|
||||
var r: Float = 0.toFloat()
|
||||
var g: Float = 0.toFloat()
|
||||
var b: Float = 0.toFloat()
|
||||
var a: Float = 0.toFloat()
|
||||
|
||||
/** Constructs a new Cvec with all components set to 0. */
|
||||
constructor() {}
|
||||
|
||||
@@ -12,8 +12,9 @@ import net.torvald.UnsafeHelper
|
||||
*/
|
||||
internal class UnsafeCvecArray(val width: Int, val height: Int) {
|
||||
|
||||
private val TOTAL_SIZE_IN_BYTES = 16L * (width + 1) * (height + 1)
|
||||
private val array = UnsafeHelper.allocate(TOTAL_SIZE_IN_BYTES)
|
||||
val TOTAL_SIZE_IN_BYTES = 16L * width * height
|
||||
|
||||
val array = UnsafeHelper.allocate(TOTAL_SIZE_IN_BYTES)
|
||||
|
||||
private inline fun toAddr(x: Int, y: Int) = 16L * (y * width + x)
|
||||
|
||||
|
||||
@@ -107,7 +107,7 @@ internal object AssembleFrameBase {
|
||||
transforms.forEach { transform ->
|
||||
if (transform.joint.name == ADProperties.ALL_JOINT_SELECT_KEY) {
|
||||
// transform applies to all joints
|
||||
for (c in out.indices) {
|
||||
for (c in 0 until out.size) {
|
||||
out[c] = out[c].first to (out[c].second + transform.translate)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,7 +20,7 @@ import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonPrimitive;
|
||||
import net.torvald.gdx.graphics.PixmapIO2;
|
||||
import net.torvald.getcpuname.GetCpuName;
|
||||
import net.torvald.terrarum.concurrent.ThreadExecutor;
|
||||
import net.torvald.terrarum.concurrent.ThreadParallel;
|
||||
import net.torvald.terrarum.controller.GdxControllerAdapter;
|
||||
import net.torvald.terrarum.controller.TerrarumController;
|
||||
import net.torvald.terrarum.controller.XinputControllerAdapter;
|
||||
@@ -33,7 +33,6 @@ import net.torvald.terrarum.modulebasegame.TerrarumIngame;
|
||||
import net.torvald.terrarum.modulebasegame.ui.ItemSlotImageFactory;
|
||||
import net.torvald.terrarum.utils.JsonFetcher;
|
||||
import net.torvald.terrarum.utils.JsonWriter;
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas;
|
||||
import net.torvald.terrarumsansbitmap.gdx.GameFontBase;
|
||||
import net.torvald.terrarumsansbitmap.gdx.TextureRegionPack;
|
||||
import net.torvald.util.ArrayListMap;
|
||||
@@ -137,7 +136,7 @@ public class AppLoader implements ApplicationListener {
|
||||
public static String renderer = "(a super-fancy virtual photoradiator)";
|
||||
public static String rendererVendor = "(aperture science psychovisualcomputation laboratory)";
|
||||
|
||||
public static int THREAD_COUNT = ThreadExecutor.INSTANCE.getThreadCount();
|
||||
public static int THREADS = ThreadParallel.INSTANCE.getThreadCount();
|
||||
public static boolean MULTITHREAD;
|
||||
|
||||
public static final boolean is32BitJVM = !System.getProperty("sun.arch.data.model").contains("64");
|
||||
@@ -209,8 +208,8 @@ public class AppLoader implements ApplicationListener {
|
||||
|
||||
public static ArrayListMap debugTimers = new ArrayListMap<String, Long>();
|
||||
|
||||
public static final int defaultW = 1280;
|
||||
public static final int defaultH = 720;
|
||||
public static final int defaultW = 1116;
|
||||
public static final int defaultH = 744;
|
||||
public static final int minimumW = 1080;
|
||||
public static final int minimumH = 720;
|
||||
|
||||
@@ -316,15 +315,13 @@ public class AppLoader implements ApplicationListener {
|
||||
ShaderProgram.pedantic = false;
|
||||
|
||||
LwjglApplicationConfiguration appConfig = new LwjglApplicationConfiguration();
|
||||
appConfig.useGL30 = false; // https://stackoverflow.com/questions/46753218/libgdx-should-i-use-gl30
|
||||
appConfig.useGL30 = true; // utilising some GL trickeries, need this to be TRUE
|
||||
appConfig.vSyncEnabled = getConfigBoolean("usevsync");
|
||||
appConfig.resizable = false;//true;
|
||||
//appConfig.width = 1110; // photographic ratio (1.5:1)
|
||||
//appConfig.height = 740; // photographic ratio (1.5:1)
|
||||
appConfig.width = getConfigInt("screenwidth");
|
||||
if (appConfig.width % 2 == 1) appConfig.width -= 1;
|
||||
if (appConfig.width < minimumW) appConfig.width = minimumW;
|
||||
appConfig.height = getConfigInt("screenheight");
|
||||
if (appConfig.height % 2 == 1) appConfig.height -= 1;
|
||||
if (appConfig.height < minimumH) appConfig.height = minimumH;
|
||||
appConfig.backgroundFPS = Math.min(GLOBAL_FRAMERATE_LIMIT, getConfigInt("displayfps"));
|
||||
appConfig.foregroundFPS = Math.min(GLOBAL_FRAMERATE_LIMIT, getConfigInt("displayfps"));
|
||||
appConfig.title = GAME_NAME;
|
||||
@@ -349,11 +346,9 @@ public class AppLoader implements ApplicationListener {
|
||||
// safe area box
|
||||
//KeyToggler.INSTANCE.forceSet(Input.Keys.F11, true);
|
||||
}
|
||||
else {
|
||||
System.err.println("Game not started using DEBUG MODE -- current build of the game will display black screen without debug mode");
|
||||
}
|
||||
|
||||
// set some more configuration vars
|
||||
MULTITHREAD = THREAD_COUNT >= 3 && getConfigBoolean("multithread");
|
||||
MULTITHREAD = ThreadParallel.INSTANCE.getThreadCount() >= 3 && getConfigBoolean("multithread");
|
||||
|
||||
new LwjglApplication(new AppLoader(appConfig), appConfig);
|
||||
}
|
||||
@@ -495,10 +490,6 @@ public class AppLoader implements ApplicationListener {
|
||||
|
||||
// make loading list
|
||||
CommonResourcePool.INSTANCE.loadAll();
|
||||
|
||||
// create tile atlas
|
||||
printdbg(this, "Making terrain textures...");
|
||||
CreateTileAtlas.INSTANCE.invoke(false);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -562,14 +553,11 @@ public class AppLoader implements ApplicationListener {
|
||||
|
||||
try {
|
||||
Pixmap p = ScreenUtils.getFrameBufferPixmap(0, 0, appConfig.width, appConfig.height);
|
||||
PixmapIO2.writeTGA(Gdx.files.absolute(defaultDir+"/Screenshot-"+String.valueOf(System.currentTimeMillis())+".tga"), p, true);
|
||||
PixmapIO2.writeTGA(Gdx.files.absolute(defaultDir + "/Screenshot.tga"), p, true);
|
||||
p.dispose();
|
||||
|
||||
Terrarum.INSTANCE.getIngame().sendNotification("Screenshot taken");
|
||||
}
|
||||
catch (Throwable e) {
|
||||
e.printStackTrace();
|
||||
Terrarum.INSTANCE.getIngame().sendNotification("Failed to take screenshot: "+e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -664,6 +652,9 @@ public class AppLoader implements ApplicationListener {
|
||||
screenW = width;
|
||||
screenH = height;
|
||||
|
||||
if (screenW % 2 == 1) screenW -= 1;
|
||||
if (screenH % 2 == 1) screenH -= 1;
|
||||
|
||||
if (currenScreen != null) currenScreen.resize(screenW, screenH);
|
||||
|
||||
|
||||
@@ -797,7 +788,7 @@ public class AppLoader implements ApplicationListener {
|
||||
currenScreen = screen;
|
||||
|
||||
currenScreen.show();
|
||||
currenScreen.resize(appConfig.width, appConfig.height);
|
||||
currenScreen.resize(Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
|
||||
|
||||
|
||||
System.gc();
|
||||
@@ -1128,21 +1119,6 @@ public class AppLoader implements ApplicationListener {
|
||||
return ((float[]) cfg);
|
||||
}
|
||||
|
||||
public static String[] getConfigStringArray(String key) {
|
||||
Object cfg = getConfigMaster(key);
|
||||
if (cfg instanceof JsonArray) {
|
||||
JsonArray jsonArray = ((JsonArray) cfg).getAsJsonArray();
|
||||
//return IntArray(jsonArray.size(), { i -> jsonArray[i].asInt })
|
||||
String[] intArray = new String[jsonArray.size()];
|
||||
for (int i = 0; i < jsonArray.size(); i++) {
|
||||
intArray[i] = jsonArray.get(i).getAsString();
|
||||
}
|
||||
return intArray;
|
||||
}
|
||||
else
|
||||
return ((String[]) cfg);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get config from config file. If the entry does not exist, get from defaults; if the entry is not in the default, NullPointerException will be thrown
|
||||
*/
|
||||
@@ -1258,4 +1234,4 @@ public class AppLoader implements ApplicationListener {
|
||||
public static long getTIME_T() {
|
||||
return System.currentTimeMillis() / 1000L;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -29,68 +29,68 @@ object DefaultConfig {
|
||||
|
||||
jsonObject.addProperty("showhealthmessageonstartup", true)
|
||||
|
||||
|
||||
// control-gamepad
|
||||
|
||||
// "config_key", "config_mouse", "config_gamepad" are keyword recognised by control setup UI
|
||||
|
||||
jsonObject.addProperty("usexinput", true) // when FALSE, LT+RT input on xbox controller is impossible
|
||||
|
||||
jsonObject.addProperty("config_gamepadkeyn", 3)
|
||||
jsonObject.addProperty("config_gamepadkeyw", 2)
|
||||
jsonObject.addProperty("config_gamepadkeys", 0)
|
||||
jsonObject.addProperty("config_gamepadkeye", 1) // xbox indices
|
||||
jsonObject.addProperty("gamepadkeyn", 3)
|
||||
jsonObject.addProperty("gamepadkeyw", 2)
|
||||
jsonObject.addProperty("gamepadkeys", 0)
|
||||
jsonObject.addProperty("gamepadkeye", 1) // xbox indices
|
||||
|
||||
jsonObject.addProperty("config_gamepadlup", 4)
|
||||
jsonObject.addProperty("config_gamepadrup", 5)
|
||||
jsonObject.addProperty("config_gamepadselect", 6)
|
||||
jsonObject.addProperty("config_gamepadstart", 7)
|
||||
jsonObject.addProperty("gamepadlup", 4)
|
||||
jsonObject.addProperty("gamepadrup", 5)
|
||||
jsonObject.addProperty("gamepadselect", 6)
|
||||
jsonObject.addProperty("gamepadstart", 7)
|
||||
|
||||
jsonObject.addProperty("config_gamepadltrigger", 8)
|
||||
jsonObject.addProperty("config_gamepadrtrigger", 9)
|
||||
jsonObject.addProperty("config_gamepadlthumb", 10)
|
||||
jsonObject.addProperty("config_gamepadrthumb", 11)
|
||||
jsonObject.addProperty("gamepadltrigger", 8)
|
||||
jsonObject.addProperty("gamepadrtrigger", 9)
|
||||
jsonObject.addProperty("gamepadlthumb", 10)
|
||||
jsonObject.addProperty("gamepadrthumb", 11)
|
||||
|
||||
|
||||
jsonObject.addProperty("config_gamepadaxislx", 1)
|
||||
jsonObject.addProperty("config_gamepadaxisly", 0)
|
||||
jsonObject.addProperty("config_gamepadaxisrx", 3)
|
||||
jsonObject.addProperty("config_gamepadaxisry", 2) // 0-1-2-3 but sometimes 3-2-1-0 ?! what the actual fuck?
|
||||
jsonObject.addProperty("config_gamepadtriggeraxis", 4) // positive: LT, negative: RT (xbox pad)
|
||||
jsonObject.addProperty("config_gamepadtriggeraxis2", 5) // just in case... (RT)
|
||||
jsonObject.addProperty("gamepadaxislx", 1)
|
||||
jsonObject.addProperty("gamepadaxisly", 0)
|
||||
jsonObject.addProperty("gamepadaxisrx", 3)
|
||||
jsonObject.addProperty("gamepadaxisry", 2) // 0-1-2-3 but sometimes 3-2-1-0 ?! what the actual fuck?
|
||||
jsonObject.addProperty("gamepadtriggeraxis", 4) // positive: LT, negative: RT (xbox pad)
|
||||
jsonObject.addProperty("gamepadtriggeraxis2", 5) // just in case... (RT)
|
||||
|
||||
val axesZeroPoints = JsonArray(); axesZeroPoints.add(-0.011f); axesZeroPoints.add(-0.022f); axesZeroPoints.add(-0.033f); axesZeroPoints.add(-0.044f)
|
||||
jsonObject.add("gamepadaxiszeropoints", axesZeroPoints) // to accomodate shifted zero point of analog stick
|
||||
|
||||
jsonObject.addProperty("gamepadlabelstyle", "msxbone") // "nwii", "logitech", "sonyps", "msxb360", "msxbone"
|
||||
|
||||
|
||||
|
||||
// control-keyboard (GDX key codes)
|
||||
jsonObject.addProperty("config_keyup", Input.Keys.E)
|
||||
jsonObject.addProperty("config_keyleft", Input.Keys.S)
|
||||
jsonObject.addProperty("config_keydown", Input.Keys.D)
|
||||
jsonObject.addProperty("config_keyright", Input.Keys.F) // ESDF Masterrace
|
||||
jsonObject.addProperty("keyup", Input.Keys.E)
|
||||
jsonObject.addProperty("keyleft", Input.Keys.S)
|
||||
jsonObject.addProperty("keydown", Input.Keys.D)
|
||||
jsonObject.addProperty("keyright", Input.Keys.F) // ESDF Masterrace
|
||||
|
||||
jsonObject.addProperty("config_keymovementaux", Input.Keys.A) // movement-auxiliary, or hookshot
|
||||
jsonObject.addProperty("config_keyinventory", Input.Keys.Q)
|
||||
jsonObject.addProperty("config_keyinteract", Input.Keys.R)
|
||||
jsonObject.addProperty("config_keyclose", Input.Keys.C) // this or hard-coded ESC
|
||||
jsonObject.addProperty("config_keyzoom", Input.Keys.Z)
|
||||
jsonObject.addProperty("keymovementaux", Input.Keys.A) // movement-auxiliary, or hookshot
|
||||
jsonObject.addProperty("keyinventory", Input.Keys.Q)
|
||||
jsonObject.addProperty("keyinteract", Input.Keys.R)
|
||||
jsonObject.addProperty("keyclose", Input.Keys.C) // this or hard-coded ESC
|
||||
jsonObject.addProperty("keyzoom", Input.Keys.Z)
|
||||
|
||||
jsonObject.addProperty("config_keygamemenu", Input.Keys.TAB)
|
||||
jsonObject.addProperty("config_keyquicksel", Input.Keys.SHIFT_LEFT) // pie menu is now LShift because GDX does not read CapsLock
|
||||
jsonObject.addProperty("keygamemenu", Input.Keys.TAB)
|
||||
jsonObject.addProperty("keyquicksel", Input.Keys.SHIFT_LEFT) // pie menu is now LShift because GDX does not read CapsLock
|
||||
val keyquickselalt = JsonArray(); keyquickselalt.add(Input.Keys.BACKSPACE); keyquickselalt.add(Input.Keys.CONTROL_LEFT); keyquickselalt.add(Input.Keys.BACKSLASH)
|
||||
// Colemak, Workman and some typers use CapsLock as Backspace, Apple-JIS and HHKB has Control in place of CapsLock and often re-assigned to Command
|
||||
// so these keys are treated as the same.
|
||||
// FOR ~~FUCKS~~ERGONOMICS' SAKE DON'T USE CTRL AND ALT AS A KEY!
|
||||
jsonObject.add("config_keyquickselalt", keyquickselalt)
|
||||
jsonObject.addProperty("config_mousequicksel", Input.Buttons.MIDDLE) // middle click to open pie menu
|
||||
jsonObject.add("keyquickselalt", keyquickselalt)
|
||||
jsonObject.addProperty("mousequicksel", Input.Buttons.MIDDLE) // middle click to open pie menu
|
||||
|
||||
jsonObject.addProperty("config_keyjump", Input.Keys.SPACE)
|
||||
jsonObject.addProperty("keyjump", Input.Keys.SPACE)
|
||||
|
||||
val keyquickslots = JsonArray(); for (i in Input.Keys.NUM_1..Input.Keys.NUM_9) keyquickslots.add(i); keyquickslots.add(Input.Keys.NUM_0) // NUM_1 to NUM_0
|
||||
jsonObject.add("config_keyquickslots", keyquickslots)
|
||||
jsonObject.add("keyquickslots", keyquickslots)
|
||||
|
||||
jsonObject.addProperty("config_mouseprimary", Input.Buttons.LEFT) // left mouse
|
||||
jsonObject.addProperty("config_mousesecondary", Input.Buttons.RIGHT) // right mouse
|
||||
jsonObject.addProperty("mouseprimary", Input.Buttons.LEFT) // left mouse
|
||||
jsonObject.addProperty("mousesecondary", Input.Buttons.RIGHT) // right mouse
|
||||
|
||||
|
||||
jsonObject.addProperty("pcgamepadenv", "console")
|
||||
@@ -111,7 +111,7 @@ object DefaultConfig {
|
||||
|
||||
// settings regarding debugger
|
||||
val buildingMakerFavs = JsonArray()
|
||||
arrayOf(
|
||||
intArrayOf(
|
||||
Block.GLASS_CRUDE,
|
||||
Block.PLANK_NORMAL,
|
||||
Block.PLANK_BIRCH,
|
||||
@@ -120,10 +120,9 @@ object DefaultConfig {
|
||||
|
||||
Block.STONE_TILE_WHITE,
|
||||
Block.TORCH,
|
||||
"wall@" + Block.PLANK_NORMAL,
|
||||
"wall@" + Block.PLANK_BIRCH,
|
||||
"wall@" + Block.GLASS_CRUDE
|
||||
).forEach {
|
||||
Block.PLANK_NORMAL + BlockCodex.MAX_TERRAIN_TILES,
|
||||
Block.PLANK_BIRCH + BlockCodex.MAX_TERRAIN_TILES,
|
||||
Block.GLASS_CRUDE + BlockCodex.MAX_TERRAIN_TILES).forEach {
|
||||
buildingMakerFavs.add(it)
|
||||
}
|
||||
jsonObject.add("buildingmakerfavs", buildingMakerFavs)
|
||||
|
||||
@@ -1172,8 +1172,8 @@ class Ingame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
ThreadParallel.map(
|
||||
i,
|
||||
ThreadActorUpdate(
|
||||
actors.div(Terrarum.THREADS).times(i).roundToInt(),
|
||||
actors.div(Terrarum.THREADS).times(i.plus(1)).roundToInt() - 1
|
||||
actors.div(Terrarum.THREADS).times(i).roundInt(),
|
||||
actors.div(Terrarum.THREADS).times(i.plus(1)).roundInt() - 1
|
||||
),
|
||||
"ActorUpdate"
|
||||
)
|
||||
|
||||
@@ -13,7 +13,6 @@ class GdxColorMap {
|
||||
|
||||
constructor(imageFile: FileHandle) {
|
||||
AppLoader.printdbg(this, "Loading colormap from ${imageFile.name()}")
|
||||
printStackTrace(this)
|
||||
|
||||
val pixmap = Pixmap(imageFile)
|
||||
width = pixmap.width
|
||||
|
||||
@@ -5,7 +5,6 @@ import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||
import com.badlogic.gdx.utils.Queue
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.gameactors.Actor
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.ActorHumanoid
|
||||
import net.torvald.terrarum.realestate.LandUtil
|
||||
@@ -142,17 +141,17 @@ open class IngameInstance(val batch: SpriteBatch) : Screen {
|
||||
*
|
||||
* Queueing schema is used to make sure things are synchronised.
|
||||
*/
|
||||
open fun queueTerrainChangedEvent(old: ItemID, new: ItemID, position: Long) {
|
||||
open fun queueTerrainChangedEvent(old: Int, new: Int, position: Long) {
|
||||
val (x, y) = LandUtil.resolveBlockAddr(world, position)
|
||||
terrainChangeQueue.addLast(BlockChangeQueueItem(old, new, x, y))
|
||||
terrainChangeQueue.addFirst(BlockChangeQueueItem(old, new, x, y))
|
||||
}
|
||||
|
||||
/**
|
||||
* Wall version of terrainChanged() event
|
||||
*/
|
||||
open fun queueWallChangedEvent(old: ItemID, new: ItemID, position: Long) {
|
||||
open fun queueWallChangedEvent(old: Int, new: Int, position: Long) {
|
||||
val (x, y) = LandUtil.resolveBlockAddr(world, position)
|
||||
wallChangeQueue.addLast(BlockChangeQueueItem(old, new, x, y))
|
||||
wallChangeQueue.addFirst(BlockChangeQueueItem(old, new, x, y))
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -161,9 +160,9 @@ open class IngameInstance(val batch: SpriteBatch) : Screen {
|
||||
* @param old previous settings of conduits in bit set format.
|
||||
* @param new current settings of conduits in bit set format.
|
||||
*/
|
||||
open fun queueWireChangedEvent(old: ItemID, new: ItemID, position: Long) {
|
||||
open fun queueWireChangedEvent(old: Int, new: Int, position: Long) {
|
||||
val (x, y) = LandUtil.resolveBlockAddr(world, position)
|
||||
wireChangeQueue.addLast(BlockChangeQueueItem(old, new, x, y))
|
||||
wireChangeQueue.addFirst(BlockChangeQueueItem(old, new, x, y))
|
||||
}
|
||||
|
||||
|
||||
@@ -253,11 +252,7 @@ open class IngameInstance(val batch: SpriteBatch) : Screen {
|
||||
|
||||
|
||||
|
||||
data class BlockChangeQueueItem(val old: ItemID, val new: ItemID, val posX: Int, val posY: Int)
|
||||
|
||||
open fun sendNotification(messages: Array<String>) {}
|
||||
open fun sendNotification(messages: List<String>) {}
|
||||
open fun sendNotification(singleMessage: String) {}
|
||||
data class BlockChangeQueueItem(val old: Int, val new: Int, val posX: Int, val posY: Int)
|
||||
}
|
||||
|
||||
inline fun Lock.lock(body: () -> Unit) {
|
||||
|
||||
@@ -4,7 +4,6 @@ import com.badlogic.gdx.Gdx
|
||||
import com.badlogic.gdx.ScreenAdapter
|
||||
import com.badlogic.gdx.graphics.OrthographicCamera
|
||||
import com.badlogic.gdx.utils.Disposable
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.util.CircularArray
|
||||
|
||||
open class LoadScreenBase : ScreenAdapter(), Disposable {
|
||||
@@ -64,8 +63,6 @@ open class LoadScreenBase : ScreenAdapter(), Disposable {
|
||||
}
|
||||
|
||||
override fun render(delta: Float) {
|
||||
Gdx.graphics.setTitle(TerrarumIngame.getCanonicalTitle())
|
||||
|
||||
if (screenToLoad?.gameInitialised ?: false) {
|
||||
doContextChange = true
|
||||
}
|
||||
|
||||
@@ -178,19 +178,16 @@ object ModMgr {
|
||||
}
|
||||
|
||||
/** Get a common file (literal file or directory) from all the installed mods. Files are guaranteed to exist. If a mod does not
|
||||
* contain the file, the mod will be skipped.
|
||||
*
|
||||
* @return List of pairs<modname, file>
|
||||
*/
|
||||
fun getFilesFromEveryMod(path: String): List<Pair<String, File>> {
|
||||
* contain the file, the mod will be skipped. */
|
||||
fun getFilesFromEveryMod(path: String): List<File> {
|
||||
val path = path.sanitisePath()
|
||||
val moduleNames = moduleInfo.keys.toList()
|
||||
|
||||
val filesList = ArrayList<Pair<String, File>>()
|
||||
val filesList = ArrayList<File>()
|
||||
moduleNames.forEach {
|
||||
val file = File(getPath(it, path))
|
||||
|
||||
if (file.exists()) filesList.add(it to file)
|
||||
if (file.exists()) filesList.add(file)
|
||||
}
|
||||
|
||||
return filesList.toList()
|
||||
@@ -199,18 +196,16 @@ object ModMgr {
|
||||
/** Get a common file (literal file or directory) from all the installed mods. Files are guaranteed to exist. If a mod does not
|
||||
* contain the file, the mod will be skipped.
|
||||
*
|
||||
* Returning files are read-only.
|
||||
* @return List of pairs<modname, filehandle>
|
||||
*/
|
||||
fun getGdxFilesFromEveryMod(path: String): List<Pair<String, FileHandle>> {
|
||||
* Returning files are read-only. */
|
||||
fun getGdxFilesFromEveryMod(path: String): List<FileHandle> {
|
||||
val path = path.sanitisePath()
|
||||
val moduleNames = moduleInfo.keys.toList()
|
||||
|
||||
val filesList = ArrayList<Pair<String, FileHandle>>()
|
||||
val filesList = ArrayList<FileHandle>()
|
||||
moduleNames.forEach {
|
||||
val file = Gdx.files.internal(getPath(it, path))
|
||||
|
||||
if (file.exists()) filesList.add(it to file)
|
||||
if (file.exists()) filesList.add(file)
|
||||
}
|
||||
|
||||
return filesList.toList()
|
||||
@@ -235,17 +230,16 @@ object ModMgr {
|
||||
@JvmStatic operator fun invoke(module: String) {
|
||||
val csv = CSVFetcher.readFromModule(module, itemPath + "itemid.csv")
|
||||
csv.forEach {
|
||||
val className: String = it["classname"].toString()
|
||||
val internalID: Int = it["id"].toInt()
|
||||
val itemName: String = "item@$module:$internalID"
|
||||
val className = it["classname"].toString()
|
||||
val itemID = it["id"].toInt()
|
||||
|
||||
printdbg(this, "Reading item ${itemName} <<- internal #$internalID with className $className")
|
||||
printdbg(this, "Reading item #$itemID with className $className")
|
||||
|
||||
val loadedClass = Class.forName(className)
|
||||
val loadedClassConstructor = loadedClass.getConstructor(ItemID::class.java)
|
||||
val loadedClassInstance = loadedClassConstructor.newInstance(itemName)
|
||||
val loadedClassInstance = loadedClassConstructor.newInstance(itemID)
|
||||
|
||||
ItemCodex[itemName] = loadedClassInstance as GameItem
|
||||
ItemCodex[itemID] = loadedClassInstance as GameItem
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -59,13 +59,6 @@ data class Point2d(var x: Double, var y: Double) : Cloneable {
|
||||
|
||||
fun toDoubleArray() = doubleArrayOf(x, y)
|
||||
|
||||
fun apply(transformation: (Double, Double) -> Pair<Double, Double>): Point2d {
|
||||
val translation = transformation(x, y)
|
||||
this.x = translation.first
|
||||
this.y = translation.second
|
||||
|
||||
return this
|
||||
}
|
||||
}
|
||||
|
||||
data class Point2i(var x: Int, var y: Int) {
|
||||
@@ -86,12 +79,4 @@ data class Point2i(var x: Int, var y: Int) {
|
||||
operator fun minus(other: Point2i): Point2i {
|
||||
return Point2i(other.x - this.x, other.y - this.y)
|
||||
}
|
||||
|
||||
fun apply(transformation: (Int, Int) -> Pair<Int, Int>): Point2i {
|
||||
val translation = transformation(x, y)
|
||||
this.x = translation.first
|
||||
this.y = translation.second
|
||||
|
||||
return this
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,7 +36,6 @@ object PostProcessor : Disposable {
|
||||
private val defaultResCol = Color(0x66ffff66)
|
||||
private val safeAreaCol = Color(0xffffff66.toInt())
|
||||
private val safeAreaCol2 = Color(0xffffff44.toInt())
|
||||
private val currentResCol = Color(0xff00ff44.toInt())
|
||||
|
||||
private val debugUI = BasicDebugInfoWindow()
|
||||
|
||||
@@ -193,14 +192,7 @@ object PostProcessor : Disposable {
|
||||
AppLoader.fontSmallNumbers.draw(
|
||||
batch, defaultResStr,
|
||||
(AppLoader.screenW - AppLoader.minimumW).div(2).toFloat(),
|
||||
(AppLoader.screenH - AppLoader.minimumH).div(2).toFloat()
|
||||
)
|
||||
|
||||
batch.color = currentResCol
|
||||
AppLoader.fontSmallNumbers.draw(
|
||||
batch, currentResStr,
|
||||
AppLoader.screenW - 80f,
|
||||
0f
|
||||
(AppLoader.screenH - AppLoader.minimumH).div(2).minus(10).toFloat()
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -214,7 +206,6 @@ object PostProcessor : Disposable {
|
||||
}
|
||||
|
||||
private val defaultResStr = "${AppLoader.minimumW}x${AppLoader.minimumH}"
|
||||
private val currentResStr = "${AppLoader.screenW}x${AppLoader.screenH}"
|
||||
private val safeAreaStr = "TV Safe Area"
|
||||
private val versionStr = "Version ${AppLoader.getVERSION_STRING()}"
|
||||
private val thisIsDebugStr = "${AppLoader.GAME_NAME} Develoment Build $versionStr"
|
||||
|
||||
@@ -6,22 +6,19 @@ package net.torvald.terrarum
|
||||
*/
|
||||
object ReferencingRanges {
|
||||
|
||||
val TILES = 0..65535 // 65 536 blocks
|
||||
val WALLS = 65536..131071 // 65 536 walls
|
||||
val WIRES = 131072..135167 // 4 096 wires
|
||||
val ITEMS_STATIC = 135168..0x0F_FFFF // 913 408 items
|
||||
val ITEMS_DYNAMIC = 0x10_0000..0x0FFF_FFFF // 267 386 880 pseudo-items
|
||||
val ACTORS = 0x1000_0000..0x7FFF_FFFF // too much actors
|
||||
val TILES = 0..4095
|
||||
val WALLS = 4096..8191
|
||||
val WIRES = 8192..8447
|
||||
val ITEMS_STATIC = 8448..0x0F_FFFF
|
||||
val ITEMS_DYNAMIC = 0x10_0000..0x0FFF_FFFF
|
||||
val ACTORS = 0x1000_0000..0x7FFF_FFFF
|
||||
|
||||
// Actor IDs are assigned in 256 groups, single actor can have 256 sub-actors
|
||||
val ACTORS_BEHIND = 0x1000_0000..0x1FFF_FFFF // Rendered behind (e.g. tapestries)
|
||||
val ACTORS_MIDDLE = 0x2000_0000..0x4FFF_FFFF // Regular actors (e.g. almost all of them)
|
||||
val ACTORS_MIDTOP = 0x5000_0000..0x5FFF_FFFF // Special (e.g. weapon swung, bullets, dropped item, particles)
|
||||
val ACTORS_FRONT = 0x6000_0000..0x6FFF_FFFF // Rendered front (e.g. fake tile)
|
||||
val ACTORS_OVERLAY = 0x7000_0000..0x7FFF_FFFF // Rendered as screen overlay, not affected by light nor environment overlays
|
||||
|
||||
val VIRTUAL_TILES = -2 downTo -1048576 // index of -1 breaks things for some reason :(
|
||||
val VIRTUAL_TILES = -2 downTo -65536 // index of -1 breaks things for some reason :(
|
||||
|
||||
val PREFIX_DYNAMICITEM = "dyn:"
|
||||
val PREFIX_ACTORITEM = "actor:"
|
||||
}
|
||||
@@ -9,7 +9,6 @@ import com.badlogic.gdx.graphics.Texture
|
||||
import com.badlogic.gdx.graphics.glutils.FrameBuffer
|
||||
import com.jme3.math.FastMath
|
||||
import net.torvald.terrarum.langpack.Lang
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.util.CircularArray
|
||||
|
||||
/**
|
||||
@@ -71,8 +70,6 @@ object SanicLoadScreen : LoadScreenBase() {
|
||||
private var messageForegroundColour = Color.WHITE
|
||||
|
||||
override fun render(delta: Float) {
|
||||
Gdx.graphics.setTitle(TerrarumIngame.getCanonicalTitle())
|
||||
|
||||
val delta = Gdx.graphics.rawDeltaTime
|
||||
|
||||
glideDispY = AppLoader.screenH - 100f - AppLoader.fontGame.lineHeight
|
||||
|
||||
@@ -11,7 +11,6 @@ import com.badlogic.gdx.graphics.glutils.FrameBuffer
|
||||
import com.badlogic.gdx.graphics.glutils.ShapeRenderer
|
||||
import com.badlogic.gdx.utils.Disposable
|
||||
import com.jme3.math.FastMath
|
||||
import net.torvald.UnsafeHelper
|
||||
import net.torvald.random.HQRNG
|
||||
import net.torvald.terrarum.AppLoader.*
|
||||
import net.torvald.terrarum.gameactors.Actor
|
||||
@@ -25,8 +24,6 @@ import net.torvald.util.CircularArray
|
||||
import java.io.File
|
||||
import java.io.PrintStream
|
||||
import kotlin.math.absoluteValue
|
||||
import kotlin.math.round
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
|
||||
|
||||
@@ -100,16 +97,12 @@ object Terrarum : Disposable {
|
||||
}
|
||||
val memNativeHeap: Int
|
||||
get() {
|
||||
nativeHeapCircularArray.appendHead((Gdx.app.nativeHeap shr 20).toInt())
|
||||
nativeHeapCircularArray.appendHead((Gdx.app.javaHeap shr 20).toInt())
|
||||
|
||||
var acc = 0
|
||||
nativeHeapCircularArray.forEach { acc = maxOf(acc, it) }
|
||||
return acc
|
||||
}
|
||||
val memUnsafe: Int
|
||||
get() {
|
||||
return (UnsafeHelper.unsafeAllocatedSize shr 20).toInt()
|
||||
}
|
||||
val memXmx: Int
|
||||
get() = (Runtime.getRuntime().maxMemory() shr 20).toInt()
|
||||
val updateRateStr: String
|
||||
@@ -340,6 +333,10 @@ inline fun FrameBuffer.inAction(camera: OrthographicCamera?, batch: SpriteBatch?
|
||||
batch?.projectionMatrix = camera?.combined
|
||||
}
|
||||
|
||||
fun Float.round(): Float {
|
||||
return Math.round(this).toFloat()
|
||||
}
|
||||
|
||||
|
||||
// ShapeRenderer alternative for rects
|
||||
fun SpriteBatch.fillRect(x: Float, y: Float, w: Float, h: Float) {
|
||||
@@ -509,10 +506,11 @@ fun Float.floor() = FastMath.floor(this).toFloat()
|
||||
fun Double.ceilInt() = Math.ceil(this).toInt()
|
||||
fun Float.ceil(): Float = FastMath.ceil(this).toFloat()
|
||||
fun Float.ceilInt() = FastMath.ceil(this)
|
||||
fun Float.round(): Float = round(this)
|
||||
fun Double.round() = Math.round(this).toDouble()
|
||||
fun Double.floor() = Math.floor(this)
|
||||
fun Double.ceil() = this.floor() + 1.0
|
||||
@Deprecated("Use kotlin.roundToInt") fun Double.roundInt(): Int = Math.round(this).toInt()
|
||||
@Deprecated("Use kotlin.roundToInt") fun Float.roundInt(): Int = Math.round(this)
|
||||
fun Double.abs() = Math.abs(this)
|
||||
fun Double.sqr() = this * this
|
||||
fun Float.sqr() = this * this
|
||||
|
||||
@@ -12,7 +12,7 @@ public class TerrarumAppConfiguration {
|
||||
//////////////////////////////////////
|
||||
|
||||
public static final String GAME_NAME = "Terrarum";
|
||||
public static final String COPYRIGHT_DATE_NAME = "Copyright 2013-2021 Torvald (minjaesong)";
|
||||
public static final String COPYRIGHT_DATE_NAME = "Copyright 2013-2020 Torvald (minjaesong)";
|
||||
|
||||
/**
|
||||
* <p>
|
||||
|
||||
@@ -292,8 +292,6 @@ class TitleScreen(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
|
||||
override fun resize(width: Int, height: Int) {
|
||||
printdbg(this, "resize() called")
|
||||
printdbg(this, "called by:")
|
||||
printStackTrace(this)
|
||||
|
||||
// Set up viewport when window is resized
|
||||
initViewPort(AppLoader.screenW, AppLoader.screenH)
|
||||
|
||||
@@ -9,7 +9,6 @@ import net.torvald.terrarum.modulebasegame.ui.UIInventoryFull
|
||||
import net.torvald.terrarum.ui.UIItem
|
||||
import net.torvald.terrarum.ui.UIItemImageButton
|
||||
import net.torvald.terrarum.ui.UIUtils
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2017-10-20.
|
||||
@@ -46,7 +45,7 @@ class UIItemInventoryCatBar(
|
||||
init {
|
||||
// place sub UIs: Image Buttons
|
||||
mainButtons = Array(catArrangement.size) { index ->
|
||||
val iconPosX = ((buttonGapSize / 2) + index * (catIcons.tileW + buttonGapSize)).roundToInt()
|
||||
val iconPosX = ((buttonGapSize / 2) + index * (catIcons.tileW + buttonGapSize)).roundInt()
|
||||
val iconPosY = 0
|
||||
|
||||
UIItemImageButton(
|
||||
@@ -76,9 +75,9 @@ class UIItemInventoryCatBar(
|
||||
|
||||
sideButtons = Array(iconIndex.size) { index ->
|
||||
val iconPosX = if (index < 2)
|
||||
(relativeStartX + sideButtonsGap + (sideButtonsGap + catIcons.tileW) * index).roundToInt()
|
||||
(relativeStartX + sideButtonsGap + (sideButtonsGap + catIcons.tileW) * index).roundInt()
|
||||
else
|
||||
(relativeStartX + width + 2 * sideButtonsGap + (sideButtonsGap + catIcons.tileW) * index).roundToInt()
|
||||
(relativeStartX + width + 2 * sideButtonsGap + (sideButtonsGap + catIcons.tileW) * index).roundInt()
|
||||
val iconPosY = 0
|
||||
|
||||
UIItemImageButton(
|
||||
|
||||
@@ -10,7 +10,6 @@ import net.torvald.terrarum.gameitem.GameItem
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIInventoryFull
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIInventoryFull.Companion.INVEN_DEBUG_MODE
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIItemInventoryCellBase
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIItemInventoryCellCommonRes
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIItemInventoryCellCommonRes.toItemCountText
|
||||
@@ -106,7 +105,7 @@ class UIItemInventoryElem(
|
||||
// this one-liner sets color
|
||||
batch.color = item!!.nameColour mul if (mouseUp) mouseOverTextCol else inactiveTextCol
|
||||
// draw name of the item
|
||||
if (INVEN_DEBUG_MODE) {
|
||||
if (AppLoader.IS_DEVELOPMENT_BUILD) {
|
||||
AppLoader.fontGame.draw(batch,
|
||||
// print static id, dynamic id, and count
|
||||
"${item!!.originalID}/${item!!.dynamicID}" + (if (amount > 0 && item!!.stackable) "$fwsp($amountString)" else if (amount != 1) "$fwsp!!$amountString!!" else ""),
|
||||
|
||||
@@ -5,128 +5,128 @@ package net.torvald.terrarum.blockproperties
|
||||
*/
|
||||
object Block {
|
||||
|
||||
const val AIR = "basegame:0" // hard coded; this is the standard
|
||||
const val AIR = 0 // hard coded; this is the standard
|
||||
|
||||
const val STONE = "basegame:16"
|
||||
const val STONE_QUARRIED = "basegame:17"
|
||||
const val STONE_TILE_WHITE = "basegame:18"
|
||||
const val STONE_BRICKS = "basegame:19"
|
||||
const val STONE = 16
|
||||
const val STONE_QUARRIED = 17
|
||||
const val STONE_TILE_WHITE = 18
|
||||
const val STONE_BRICKS = 19
|
||||
|
||||
const val DIRT = "basegame:32"
|
||||
const val GRASS = "basegame:33"
|
||||
const val GRASSWALL = "basegame:34"
|
||||
const val DIRT = 32
|
||||
const val GRASS = 33
|
||||
const val GRASSWALL = 34
|
||||
|
||||
const val PLANK_NORMAL = "basegame:48"
|
||||
const val PLANK_EBONY = "basegame:49"
|
||||
const val PLANK_BIRCH = "basegame:50"
|
||||
const val PLANK_BLOODROSE = "basegame:51"
|
||||
const val PLANK_NORMAL = 48
|
||||
const val PLANK_EBONY = 49
|
||||
const val PLANK_BIRCH = 50
|
||||
const val PLANK_BLOODROSE = 51
|
||||
|
||||
const val TRUNK_NORMAL = "basegame:64"
|
||||
const val TRUNK_EBONY = "basegame:65"
|
||||
const val TRUNK_BIRCH = "basegame:66"
|
||||
const val TRUNK_BLOODROSE = "basegame:67"
|
||||
const val TRUNK_NORMAL = 64
|
||||
const val TRUNK_EBONY = 65
|
||||
const val TRUNK_BIRCH = 66
|
||||
const val TRUNK_BLOODROSE = 67
|
||||
|
||||
const val SAND = "basegame:80"
|
||||
const val SAND_WHITE = "basegame:81"
|
||||
const val SAND_RED = "basegame:82"
|
||||
const val SAND_DESERT = "basegame:83"
|
||||
const val SAND_BLACK = "basegame:84"
|
||||
const val SAND_GREEN = "basegame:85"
|
||||
const val SAND = 80
|
||||
const val SAND_WHITE = 81
|
||||
const val SAND_RED = 82
|
||||
const val SAND_DESERT = 83
|
||||
const val SAND_BLACK = 84
|
||||
const val SAND_GREEN = 85
|
||||
|
||||
const val GRAVEL = "basegame:96"
|
||||
const val GRAVEL_GREY = "basegame:97"
|
||||
const val GRAVEL = 96
|
||||
const val GRAVEL_GREY = 97
|
||||
|
||||
const val ORE_COPPER = "basegame:112"
|
||||
const val ORE_IRON = "basegame:113"
|
||||
const val ORE_GOLD = "basegame:114"
|
||||
const val ORE_SILVER = "basegame:115"
|
||||
const val ORE_ILMENITE = "basegame:116"
|
||||
const val ORE_AURICHALCUM = "basegame:117"
|
||||
const val ORE_COPPER = 112
|
||||
const val ORE_IRON = 113
|
||||
const val ORE_GOLD = 114
|
||||
const val ORE_SILVER = 115
|
||||
const val ORE_ILMENITE = 116
|
||||
const val ORE_AURICHALCUM = 117
|
||||
|
||||
const val RAW_RUBY = "basegame:128"
|
||||
const val RAW_EMERALD = "basegame:129"
|
||||
const val RAW_SAPPHIRE = "basegame:130"
|
||||
const val RAW_TOPAZ = "basegame:131"
|
||||
const val RAW_DIAMOND = "basegame:132"
|
||||
const val RAW_AMETHYST = "basegame:133"
|
||||
const val RAW_RUBY = 128
|
||||
const val RAW_EMERALD = 129
|
||||
const val RAW_SAPPHIRE = 130
|
||||
const val RAW_TOPAZ = 131
|
||||
const val RAW_DIAMOND = 132
|
||||
const val RAW_AMETHYST = 133
|
||||
|
||||
const val SNOW = "basegame:144"
|
||||
const val ICE_FRAGILE = "basegame:145"
|
||||
const val ICE_NATURAL = "basegame:146"
|
||||
const val ICE_MAGICAL = "basegame:147"
|
||||
const val SNOW = 144
|
||||
const val ICE_FRAGILE = 145
|
||||
const val ICE_NATURAL = 146
|
||||
const val ICE_MAGICAL = 147
|
||||
|
||||
const val GLASS_CRUDE = "basegame:148"
|
||||
const val GLASS_CLEAN = "basegame:149"
|
||||
const val GLASS_CRUDE = 148
|
||||
const val GLASS_CLEAN = 149
|
||||
|
||||
const val PLATFORM_STONE = "basegame:160"
|
||||
const val PLATFORM_WOODEN = "basegame:161"
|
||||
const val PLATFORM_EBONY = "basegame:162"
|
||||
const val PLATFORM_BIRCH = "basegame:163"
|
||||
const val PLATFORM_BLOODROSE = "basegame:164"
|
||||
const val PLATFORM_STONE = 160
|
||||
const val PLATFORM_WOODEN = 161
|
||||
const val PLATFORM_EBONY = 162
|
||||
const val PLATFORM_BIRCH = 163
|
||||
const val PLATFORM_BLOODROSE = 164
|
||||
|
||||
const val TORCH = "basegame:176"
|
||||
const val TORCH_FROST = "basegame:177"
|
||||
const val TORCH = 176
|
||||
const val TORCH_FROST = 177
|
||||
|
||||
const val TORCH_OFF = "basegame:192"
|
||||
const val TORCH_FROST_OFF = "basegame:193"
|
||||
const val TORCH_OFF = 192
|
||||
const val TORCH_FROST_OFF = 193
|
||||
|
||||
const val ILLUMINATOR_WHITE = "basegame:208"
|
||||
const val ILLUMINATOR_YELLOW = "basegame:209"
|
||||
const val ILLUMINATOR_ORANGE = "basegame:210"
|
||||
const val ILLUMINATOR_RED = "basegame:211"
|
||||
const val ILLUMINATOR_FUCHSIA = "basegame:212"
|
||||
const val ILLUMINATOR_PURPLE = "basegame:213"
|
||||
const val ILLUMINATOR_BLUE = "basegame:214"
|
||||
const val ILLUMINATOR_CYAN = "basegame:215"
|
||||
const val ILLUMINATOR_GREEN = "basegame:216"
|
||||
const val ILLUMINATOR_GREEN_DARK = "basegame:217"
|
||||
const val ILLUMINATOR_BROWN = "basegame:218"
|
||||
const val ILLUMINATOR_TAN = "basegame:219"
|
||||
const val ILLUMINATOR_GREY_LIGHT = "basegame:220"
|
||||
const val ILLUMINATOR_GREY_MED = "basegame:221"
|
||||
const val ILLUMINATOR_GREY_DARK = "basegame:222"
|
||||
const val ILLUMINATOR_BLACK = "basegame:223"
|
||||
const val ILLUMINATOR_WHITE = 208
|
||||
const val ILLUMINATOR_YELLOW = 209
|
||||
const val ILLUMINATOR_ORANGE = 210
|
||||
const val ILLUMINATOR_RED = 211
|
||||
const val ILLUMINATOR_FUCHSIA = 212
|
||||
const val ILLUMINATOR_PURPLE = 213
|
||||
const val ILLUMINATOR_BLUE = 214
|
||||
const val ILLUMINATOR_CYAN = 215
|
||||
const val ILLUMINATOR_GREEN = 216
|
||||
const val ILLUMINATOR_GREEN_DARK = 217
|
||||
const val ILLUMINATOR_BROWN = 218
|
||||
const val ILLUMINATOR_TAN = 219
|
||||
const val ILLUMINATOR_GREY_LIGHT = 220
|
||||
const val ILLUMINATOR_GREY_MED = 221
|
||||
const val ILLUMINATOR_GREY_DARK = 222
|
||||
const val ILLUMINATOR_BLACK = 223
|
||||
|
||||
const val ILLUMINATOR_WHITE_OFF = "basegame:224"
|
||||
const val ILLUMINATOR_YELLOW_OFF = "basegame:225"
|
||||
const val ILLUMINATOR_ORANGE_OFF = "basegame:226"
|
||||
const val ILLUMINATOR_RED_OFF = "basegame:227"
|
||||
const val ILLUMINATOR_FUCHSIA_OFF = "basegame:228"
|
||||
const val ILLUMINATOR_PURPLE_OFF = "basegame:229"
|
||||
const val ILLUMINATOR_BLUE_OFF = "basegame:230"
|
||||
const val ILLUMINATOR_CYAN_OFF = "basegame:231"
|
||||
const val ILLUMINATOR_GREEN_OFF = "basegame:232"
|
||||
const val ILLUMINATOR_GREEN_DARK_OFF = "basegame:233"
|
||||
const val ILLUMINATOR_BROWN_OFF = "basegame:234"
|
||||
const val ILLUMINATOR_TAN_OFF = "basegame:235"
|
||||
const val ILLUMINATOR_GREY_LIGHT_OFF = "basegame:236"
|
||||
const val ILLUMINATOR_GREY_MED_OFF = "basegame:237"
|
||||
const val ILLUMINATOR_GREY_DARK_OFF = "basegame:238"
|
||||
const val ILLUMINATOR_BLACK_OFF = "basegame:239"
|
||||
const val ILLUMINATOR_WHITE_OFF = 224
|
||||
const val ILLUMINATOR_YELLOW_OFF = 225
|
||||
const val ILLUMINATOR_ORANGE_OFF = 226
|
||||
const val ILLUMINATOR_RED_OFF = 227
|
||||
const val ILLUMINATOR_FUCHSIA_OFF = 228
|
||||
const val ILLUMINATOR_PURPLE_OFF = 229
|
||||
const val ILLUMINATOR_BLUE_OFF = 230
|
||||
const val ILLUMINATOR_CYAN_OFF = 231
|
||||
const val ILLUMINATOR_GREEN_OFF = 232
|
||||
const val ILLUMINATOR_GREEN_DARK_OFF = 233
|
||||
const val ILLUMINATOR_BROWN_OFF = 234
|
||||
const val ILLUMINATOR_TAN_OFF = 235
|
||||
const val ILLUMINATOR_GREY_LIGHT_OFF = 236
|
||||
const val ILLUMINATOR_GREY_MED_OFF = 237
|
||||
const val ILLUMINATOR_GREY_DARK_OFF = 238
|
||||
const val ILLUMINATOR_BLACK_OFF = 239
|
||||
|
||||
const val SANDSTONE = "basegame:240"
|
||||
const val SANDSTONE_WHITE = "basegame:241"
|
||||
const val SANDSTONE_RED = "basegame:242"
|
||||
const val SANDSTONE_DESERT = "basegame:243"
|
||||
const val SANDSTONE_BLACK = "basegame:244"
|
||||
const val SANDSTONE_GREEN = "basegame:245"
|
||||
const val SANDSTONE = 240
|
||||
const val SANDSTONE_WHITE = 241
|
||||
const val SANDSTONE_RED = 242
|
||||
const val SANDSTONE_DESERT = 243
|
||||
const val SANDSTONE_BLACK = 244
|
||||
const val SANDSTONE_GREEN = 245
|
||||
|
||||
const val LANTERN = "basegame:256"
|
||||
const val SUNSTONE = "basegame:257"
|
||||
const val DAYLIGHT_CAPACITOR = "basegame:258"
|
||||
const val LANTERN = 256
|
||||
const val SUNSTONE = 257
|
||||
const val DAYLIGHT_CAPACITOR = 258
|
||||
|
||||
|
||||
const val ACTORBLOCK_NO_COLLISION = "basegame:4091"
|
||||
const val ACTORBLOCK_FULL_COLLISION = "basegame:4092"
|
||||
const val ACTORBLOCK_ALLOW_MOVE_DOWN = "basegame:4093"
|
||||
const val ACTORBLOCK_NO_PASS_RIGHT = "basegame:4094"
|
||||
const val ACTORBLOCK_NO_PASS_LEFT = "basegame:4095"
|
||||
const val ACTORBLOCK_NO_COLLISION = 4091
|
||||
const val ACTORBLOCK_FULL_COLLISION = 4092
|
||||
const val ACTORBLOCK_ALLOW_MOVE_DOWN = 4093
|
||||
const val ACTORBLOCK_NO_PASS_RIGHT = 4094
|
||||
const val ACTORBLOCK_NO_PASS_LEFT = 4095
|
||||
|
||||
|
||||
const val LAVA = "basegame:4094"
|
||||
const val WATER = "basegame:4095"
|
||||
const val LAVA = 4094
|
||||
const val WATER = 4095
|
||||
|
||||
const val NULL = "basegame:-1"
|
||||
const val NULL = -1
|
||||
|
||||
val actorblocks = listOf(
|
||||
ACTORBLOCK_NO_COLLISION,
|
||||
|
||||
@@ -5,7 +5,6 @@ import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.AppLoader.printmsg
|
||||
import net.torvald.terrarum.ReferencingRanges
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.FluidType
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.utils.CSVFetcher
|
||||
@@ -19,12 +18,12 @@ import java.io.IOException
|
||||
*/
|
||||
object BlockCodex {
|
||||
|
||||
private var blockProps = HashMap<ItemID, BlockProp>()
|
||||
private var blockProps = HashMap<Int, BlockProp>()
|
||||
|
||||
val dynamicLights = SortedArrayList<ItemID>() // does not include virtual ones
|
||||
val dynamicLights = SortedArrayList<Int>() // does not include virtual ones
|
||||
|
||||
/** 65536 */
|
||||
//val MAX_TERRAIN_TILES = GameWorld.TILES_SUPPORTED
|
||||
/** 4096 */
|
||||
val MAX_TERRAIN_TILES = GameWorld.TILES_SUPPORTED
|
||||
|
||||
private val nullProp = BlockProp()
|
||||
|
||||
@@ -33,17 +32,12 @@ object BlockCodex {
|
||||
|
||||
// fake props for "randomised" dynamic lights
|
||||
const val DYNAMIC_RANDOM_CASES = 64
|
||||
private var virtualTileCursor = 1
|
||||
|
||||
/**
|
||||
* One-to-Many
|
||||
*/
|
||||
val tileToVirtual = HashMap<ItemID, List<ItemID>>()
|
||||
|
||||
/**
|
||||
* Many-to-One
|
||||
*/
|
||||
val virtualToTile = HashMap<ItemID, ItemID>()
|
||||
var virtualPropsCount = 0
|
||||
private set
|
||||
/** always points to the HIGHEST prop ID. <Original ID, Virtual ID> */
|
||||
val dynamicToVirtualPropMapping = ArrayList<Pair<Int, Int>>()
|
||||
/** for random access dont iterate over this */
|
||||
val dynamicToVirtualMap = hashMapOf<Int, Int>()
|
||||
|
||||
/**
|
||||
* Later entry (possible from other modules) will replace older ones
|
||||
@@ -62,28 +56,27 @@ object BlockCodex {
|
||||
setProp(blockProps[intVal(it, "id")], it)
|
||||
}*/
|
||||
|
||||
setProp(module, intVal(it, "id"), it)
|
||||
val tileId = "$module:${intVal(it, "id")}"
|
||||
val id = intVal(it, "id")
|
||||
setProp(id, it)
|
||||
|
||||
// register tiles with dynamic light
|
||||
if ((blockProps[tileId]?.dynamicLuminosityFunction ?: 0) != 0) {
|
||||
dynamicLights.add(tileId)
|
||||
if ((blockProps[id]?.dynamicLuminosityFunction ?: 0) != 0) {
|
||||
dynamicLights.add(id)
|
||||
|
||||
// add virtual props for dynamic lights
|
||||
val virtualChunk = ArrayList<ItemID>()
|
||||
repeat(DYNAMIC_RANDOM_CASES) { _ ->
|
||||
val virtualID = "virt:$virtualTileCursor"
|
||||
val virtualIDMax = ReferencingRanges.VIRTUAL_TILES.first - virtualPropsCount
|
||||
dynamicToVirtualPropMapping.add(id to virtualIDMax)
|
||||
dynamicToVirtualMap[id] = virtualIDMax
|
||||
repeat(DYNAMIC_RANDOM_CASES) { i ->
|
||||
setProp(virtualIDMax - i, it)
|
||||
printdbg(this, "Block ID $id -> Virtual ID ${virtualIDMax - i}, baseLum: ${blockProps[virtualIDMax - i]?.baseLumCol}")
|
||||
|
||||
virtualToTile[virtualID] = tileId
|
||||
virtualChunk.add(virtualID)
|
||||
|
||||
setProp("virt", virtualTileCursor, it)
|
||||
|
||||
printdbg(this, "Block ID $tileId -> Virtual ID $virtualID, baseLum: ${blockProps[virtualID]?.baseLumCol}")
|
||||
virtualTileCursor += 1
|
||||
virtualPropsCount += 1
|
||||
}
|
||||
tileToVirtual[tileId] = virtualChunk.sorted().toList()
|
||||
}
|
||||
|
||||
if (id > highestNumber)
|
||||
highestNumber = id
|
||||
}
|
||||
}
|
||||
catch (e: IOException) {
|
||||
@@ -91,8 +84,6 @@ object BlockCodex {
|
||||
}
|
||||
}
|
||||
|
||||
fun getAll() = blockProps.values
|
||||
|
||||
/*fun get(index: Int): BlockProp {
|
||||
try {
|
||||
return blockProps[index]
|
||||
@@ -106,7 +97,7 @@ object BlockCodex {
|
||||
}
|
||||
}*/
|
||||
|
||||
/*operator fun get(rawIndex: Int?): BlockProp {
|
||||
operator fun get(rawIndex: Int?): BlockProp {
|
||||
if (rawIndex == null || rawIndex == Block.NULL) {
|
||||
return nullProp
|
||||
}
|
||||
@@ -117,59 +108,45 @@ object BlockCodex {
|
||||
catch (e: NullPointerException) {
|
||||
throw NullPointerException("Blockprop with raw id $rawIndex does not exist.")
|
||||
}
|
||||
}*/
|
||||
operator fun get(blockID: ItemID?): BlockProp {
|
||||
if (blockID == null || blockID == "basegame:"+Block.NULL) {
|
||||
return nullProp
|
||||
}
|
||||
|
||||
try {
|
||||
return blockProps[blockID]!!
|
||||
}
|
||||
catch (e: NullPointerException) {
|
||||
throw NullPointerException("Blockprop with id $blockID does not exist.")
|
||||
}
|
||||
}
|
||||
|
||||
operator fun get(fluidType: FluidType?): BlockProp {
|
||||
// TODO fluid from other mods
|
||||
|
||||
if (fluidType == null || fluidType.value == 0) {
|
||||
return blockProps["basegame:"+Block.AIR]!!
|
||||
return blockProps[Block.AIR]!!
|
||||
}
|
||||
|
||||
try {
|
||||
return blockProps["basegame:${fluidType.abs() + GameWorld.TILES_SUPPORTED - 1}"]!!
|
||||
return blockProps[fluidType.abs() + GameWorld.TILES_SUPPORTED - 1]!!
|
||||
}
|
||||
catch (e: NullPointerException) {
|
||||
throw NullPointerException("Blockprop with id $fluidType does not exist.")
|
||||
throw NullPointerException("Blockprop with raw id $fluidType does not exist.")
|
||||
}
|
||||
}
|
||||
|
||||
fun getOrNull(blockID: ItemID?): BlockProp? {//<O>
|
||||
return blockProps[blockID]
|
||||
fun getOrNull(rawIndex: Int?): BlockProp? {//<O>
|
||||
return blockProps[rawIndex]
|
||||
}
|
||||
|
||||
private fun setProp(modname: String, key: Int, record: CSVRecord) {
|
||||
private fun setProp(key: Int, record: CSVRecord) {
|
||||
val prop = BlockProp()
|
||||
prop.nameKey = record.get("name")
|
||||
|
||||
prop.id = "$modname:$key"
|
||||
prop.drop = "$modname:${intVal(record, "drop")}"
|
||||
prop.id = if (key == -1) 0 else intVal(record, "id")
|
||||
prop.drop = intVal(record, "drop")
|
||||
|
||||
prop.shadeColR = floatVal(record, "shdr")
|
||||
prop.shadeColG = floatVal(record, "shdg")
|
||||
prop.shadeColB = floatVal(record, "shdb")
|
||||
prop.shadeColA = floatVal(record, "shduv")
|
||||
prop.shadeColR = floatVal(record, "shdr") / LightmapRenderer.MUL_FLOAT
|
||||
prop.shadeColG = floatVal(record, "shdg") / LightmapRenderer.MUL_FLOAT
|
||||
prop.shadeColB = floatVal(record, "shdb") / LightmapRenderer.MUL_FLOAT
|
||||
prop.shadeColA = floatVal(record, "shduv") / LightmapRenderer.MUL_FLOAT
|
||||
prop.opacity = Cvec(prop.shadeColR, prop.shadeColG, prop.shadeColB, prop.shadeColA)
|
||||
|
||||
prop.strength = intVal(record, "str")
|
||||
prop.density = intVal(record, "dsty")
|
||||
|
||||
prop.baseLumColR = floatVal(record, "lumr")
|
||||
prop.baseLumColG = floatVal(record, "lumg")
|
||||
prop.baseLumColB = floatVal(record, "lumb")
|
||||
prop.baseLumColA = floatVal(record, "lumuv")
|
||||
prop.baseLumColR = floatVal(record, "lumr") / LightmapRenderer.MUL_FLOAT
|
||||
prop.baseLumColG = floatVal(record, "lumg") / LightmapRenderer.MUL_FLOAT
|
||||
prop.baseLumColB = floatVal(record, "lumb") / LightmapRenderer.MUL_FLOAT
|
||||
prop.baseLumColA = floatVal(record, "lumuv") / LightmapRenderer.MUL_FLOAT
|
||||
prop.baseLumCol.set(prop.baseLumColR, prop.baseLumColG, prop.baseLumColB, prop.baseLumColA)
|
||||
|
||||
prop.friction = intVal(record, "fr")
|
||||
@@ -186,9 +163,9 @@ object BlockCodex {
|
||||
|
||||
prop.dynamicLuminosityFunction = intVal(record, "dlfn")
|
||||
|
||||
blockProps[prop.id] = prop
|
||||
blockProps[key] = prop
|
||||
|
||||
printmsg(this, "Setting prop ${prop.id} ->>\t${prop.nameKey}\tsolid:${prop.isSolid}")
|
||||
printmsg(this, "${intVal(record, "id")}\t" + prop.nameKey)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@ package net.torvald.terrarum.blockproperties
|
||||
|
||||
import net.torvald.gdx.graphics.Cvec
|
||||
import net.torvald.random.XXHash32
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.fmod
|
||||
import net.torvald.terrarum.serialise.toLittle
|
||||
|
||||
@@ -11,7 +10,7 @@ import net.torvald.terrarum.serialise.toLittle
|
||||
*/
|
||||
class BlockProp {
|
||||
|
||||
var id: ItemID = ""
|
||||
var id: Int = 0
|
||||
|
||||
var nameKey: String = ""
|
||||
|
||||
@@ -63,14 +62,14 @@ class BlockProp {
|
||||
baseLumCol
|
||||
} else {
|
||||
val offset = XXHash32.hash(((x and 0xFFFF).shl(16) or (y and 0xFFFF)).toLittle(), 10000).fmod(BlockCodex.DYNAMIC_RANDOM_CASES)
|
||||
BlockCodex[BlockCodex.tileToVirtual[id]!![offset]]._lumCol
|
||||
BlockCodex[BlockCodex.dynamicToVirtualMap[id]!! - offset]._lumCol
|
||||
}
|
||||
|
||||
fun getLumCol(x: Int, y: Int, channel: Int): Float = if (dynamicLuminosityFunction == 0) {
|
||||
baseLumCol.getElem(channel)
|
||||
} else {
|
||||
val offset = XXHash32.hash(((x and 0xFFFF).shl(16) or (y and 0xFFFF)).toLittle(), 10000).fmod(BlockCodex.DYNAMIC_RANDOM_CASES)
|
||||
BlockCodex[BlockCodex.tileToVirtual[id]!![offset]]._lumCol.getElem(channel)
|
||||
BlockCodex[BlockCodex.dynamicToVirtualMap[id]!! - offset]._lumCol.getElem(channel)
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -81,7 +80,7 @@ class BlockProp {
|
||||
|
||||
//fun getLum(channel: Int) = lumCol.getElem(channel)
|
||||
|
||||
var drop: ItemID = ""
|
||||
var drop: Int = 0
|
||||
|
||||
var maxSupport: Int = -1 // couldn't use NULL at all...
|
||||
|
||||
|
||||
@@ -71,34 +71,36 @@ object BlockPropUtil {
|
||||
catch (skip: NullPointerException) {}
|
||||
}*/
|
||||
// update randomised virtual props instead
|
||||
for (key in BlockCodex.tileToVirtual.values.flatten()) {
|
||||
val prop = BlockCodex[key]
|
||||
val domain = when (prop.dynamicLuminosityFunction) {
|
||||
1 -> flickerFuncDomain
|
||||
4 -> breathCycleDuration
|
||||
5 -> pulsateCycleDuration
|
||||
else -> 0f
|
||||
for (keyMax in BlockCodex.dynamicToVirtualPropMapping) {
|
||||
repeat(BlockCodex.DYNAMIC_RANDOM_CASES) {
|
||||
val prop = BlockCodex[keyMax.second - it]
|
||||
val domain = when (prop.dynamicLuminosityFunction) {
|
||||
1 -> flickerFuncDomain
|
||||
4 -> breathCycleDuration
|
||||
5 -> pulsateCycleDuration
|
||||
else -> 0f
|
||||
}
|
||||
|
||||
// FPS-time compensation
|
||||
if (Gdx.graphics.framesPerSecond > 0) {
|
||||
prop.rngBase0 += Gdx.graphics.rawDeltaTime
|
||||
}
|
||||
|
||||
// reset timer
|
||||
if (prop.rngBase0 > domain) {
|
||||
prop.rngBase0 -= domain
|
||||
|
||||
// flicker related
|
||||
prop.rngBase1 = prop.rngBase2
|
||||
prop.rngBase2 = getNewRandom()
|
||||
}
|
||||
|
||||
prop._lumCol.set(getDynamicLumFunc(prop))
|
||||
//prop.lumColR = prop.lumCol.r
|
||||
//prop.lumColG = prop.lumCol.g
|
||||
//prop.lumColB = prop.lumCol.b
|
||||
//prop.lumColA = prop.lumCol.a
|
||||
}
|
||||
|
||||
// FPS-time compensation
|
||||
if (Gdx.graphics.framesPerSecond > 0) {
|
||||
prop.rngBase0 += Gdx.graphics.rawDeltaTime
|
||||
}
|
||||
|
||||
// reset timer
|
||||
if (prop.rngBase0 > domain) {
|
||||
prop.rngBase0 -= domain
|
||||
|
||||
// flicker related
|
||||
prop.rngBase1 = prop.rngBase2
|
||||
prop.rngBase2 = getNewRandom()
|
||||
}
|
||||
|
||||
prop._lumCol.set(getDynamicLumFunc(prop))
|
||||
//prop.lumColR = prop.lumCol.r
|
||||
//prop.lumColG = prop.lumCol.g
|
||||
//prop.lumColB = prop.lumCol.b
|
||||
//prop.lumColA = prop.lumCol.a
|
||||
}
|
||||
}
|
||||
|
||||
@@ -109,8 +111,8 @@ object BlockPropUtil {
|
||||
private fun getDynamicLumFunc(prop: BlockProp): Cvec {
|
||||
return when (prop.dynamicLuminosityFunction) {
|
||||
1 -> getTorchFlicker(prop)
|
||||
2 -> (Terrarum.ingame!!.world).globalLight.cpy() // current global light
|
||||
3 -> WeatherMixer.getGlobalLightOfTime(Terrarum.ingame!!.world, WorldTime.DAY_LENGTH / 2).cpy() // daylight at noon
|
||||
2 -> (Terrarum.ingame!!.world).globalLight.cpy().mul(LightmapRenderer.DIV_FLOAT) // current global light
|
||||
3 -> WeatherMixer.getGlobalLightOfTime(Terrarum.ingame!!.world, WorldTime.DAY_LENGTH / 2).cpy().mul(LightmapRenderer.DIV_FLOAT) // daylight at noon
|
||||
4 -> getSlowBreath(prop)
|
||||
5 -> getPulsate(prop)
|
||||
else -> prop.baseLumCol
|
||||
|
||||
@@ -3,7 +3,6 @@ package net.torvald.terrarum.blockstats
|
||||
import com.jme3.math.FastMath
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.terrarum.worlddrawer.BlocksDrawer
|
||||
@@ -15,7 +14,7 @@ import java.util.*
|
||||
*/
|
||||
object BlockStats {
|
||||
|
||||
private val tilestat = HashMap<ItemID, Int>()
|
||||
private val tilestat = ShortArray(GameWorld.TILES_SUPPORTED)
|
||||
|
||||
private val TSIZE = CreateTileAtlas.TILE_SIZE
|
||||
|
||||
@@ -23,7 +22,7 @@ object BlockStats {
|
||||
* Update tile stats from tiles on screen
|
||||
*/
|
||||
fun update() {
|
||||
tilestat.clear()
|
||||
Arrays.fill(tilestat, 0.toShort())
|
||||
|
||||
// Get stats on no-zoomed screen area. In other words, will behave as if screen zoom were 1.0
|
||||
// no matter how the screen is zoomed.
|
||||
@@ -48,14 +47,29 @@ object BlockStats {
|
||||
for (x in for_x_start..for_x_end - 1) {
|
||||
val tileWall = map.getTileFromWall(x, y)
|
||||
val tileTerrain = map.getTileFromTerrain(x, y)
|
||||
tilestat[tileWall] = 1 + (tilestat[tileWall] ?: 0)
|
||||
tilestat[tileTerrain] = 1 + (tilestat[tileTerrain] ?: 0)
|
||||
++tilestat[tileWall ?: 0]
|
||||
++tilestat[tileTerrain ?: 0]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun getCount(vararg tiles: ItemID): Int {
|
||||
return tiles.fold(0) { acc, key -> acc + (tilestat[key] ?: 0) }
|
||||
fun getCount(vararg tile: Byte): Int {
|
||||
var sum = 0
|
||||
for (i in tile.indices) {
|
||||
val newArgs = java.lang.Byte.toUnsignedInt(tile[i])
|
||||
sum += java.lang.Short.toUnsignedInt(tilestat[newArgs])
|
||||
}
|
||||
|
||||
return sum
|
||||
}
|
||||
|
||||
fun getCount(vararg tile: Int): Int {
|
||||
var sum = 0
|
||||
for (i in tile.indices) {
|
||||
sum += java.lang.Short.toUnsignedInt(tilestat[tile[i]])
|
||||
}
|
||||
return sum
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -59,7 +59,7 @@ object MinimapComposer : Disposable {
|
||||
private val liveTilesMeta = Array(TILES_IN_X * TILES_IN_Y) { LiveTileMeta(revalidate = true) }
|
||||
|
||||
private val updaterQueue = Queue<Runnable>(TILES_IN_X * TILES_IN_Y * 2)
|
||||
private var currentThreads = Array(maxOf(1, AppLoader.THREAD_COUNT.times(2).div(3))) {
|
||||
private var currentThreads = Array(maxOf(1, AppLoader.THREADS.times(2).div(3))) {
|
||||
Thread()
|
||||
}
|
||||
|
||||
@@ -73,8 +73,8 @@ object MinimapComposer : Disposable {
|
||||
fun update() {
|
||||
// make the queueing work
|
||||
// enqueue first
|
||||
for (y in tilemap.indices) {
|
||||
for (x in tilemap[0].indices) {
|
||||
for (y in 0 until tilemap.size) {
|
||||
for (x in 0 until tilemap[0].size) {
|
||||
if (liveTilesMeta[tilemap[y][x]].revalidate) {
|
||||
liveTilesMeta[tilemap[y][x]].revalidate = false
|
||||
updaterQueue.addLast(createUpdater(x, y))
|
||||
@@ -83,7 +83,7 @@ object MinimapComposer : Disposable {
|
||||
}
|
||||
}
|
||||
// consume the queue
|
||||
for (k in currentThreads.indices) {
|
||||
for (k in 0 until currentThreads.size) {
|
||||
if (currentThreads[k].state == Thread.State.TERMINATED && !updaterQueue.isEmpty) {
|
||||
currentThreads[k] = Thread(updaterQueue.removeFirst(), "MinimapLivetilePainter")
|
||||
printdbg(this, "Consuming from queue; queue size now: ${updaterQueue.size}")
|
||||
@@ -134,16 +134,16 @@ object MinimapComposer : Disposable {
|
||||
|
||||
for (y in topLeftY until topLeftY + LIVETILE_SIZE) {
|
||||
for (x in if (tileSlotIndexY >= TILES_IN_X / 2) (topLeftX + LIVETILE_SIZE - 1) downTo topLeftX else topLeftX until topLeftX + LIVETILE_SIZE) {
|
||||
val tileTerr = world.getTileFromTerrain(x, y)
|
||||
val wallTerr = world.getTileFromWall(x, y)
|
||||
val colTerr = CreateTileAtlas.terrainTileColourMap.get(tileTerr)!!.toGdxColor()
|
||||
val colWall = CreateTileAtlas.terrainTileColourMap.get(wallTerr)!!.toGdxColor().mul(CreateTileAtlas.wallOverlayColour)
|
||||
val tileTerr = world.getTileFromTerrain(x, y) ?: throw Error("OoB: $x, $y")
|
||||
val wallTerr = world.getTileFromWall(x, y) ?: Block.AIR
|
||||
val colTerr = CreateTileAtlas.terrainTileColourMap.get(tileTerr % 16, tileTerr / 16)
|
||||
val colWall = CreateTileAtlas.terrainTileColourMap.get(wallTerr % 16, wallTerr / 16).mul(BlocksDrawer.wallOverlayColour)
|
||||
|
||||
val outCol = if (colTerr.a > 0.1f) colTerr else colWall
|
||||
|
||||
pixmap.blending = Pixmap.Blending.None
|
||||
pixmap.setColor(outCol)
|
||||
//pixmap.setColor(Color.CORAL)
|
||||
if (colTerr.a < 1f) {
|
||||
pixmap.setColor(colWall)
|
||||
pixmap.drawPixel(x - topLeftX, y - topLeftY)
|
||||
}
|
||||
pixmap.setColor(colTerr)
|
||||
pixmap.drawPixel(x - topLeftX, y - topLeftY)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,137 +0,0 @@
|
||||
package net.torvald.terrarum.concurrent
|
||||
|
||||
import java.util.concurrent.*
|
||||
import kotlin.math.absoluteValue
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
typealias RunnableFun = () -> Unit
|
||||
/** Int: index of the processing core */
|
||||
typealias ThreadableFun = (Int) -> Unit
|
||||
|
||||
|
||||
object ThreadExecutor {
|
||||
val threadCount = Runtime.getRuntime().availableProcessors() // not using (logicalCores + 1) method; it's often better idea to reserve one extra thread for other jobs in the app
|
||||
private lateinit var executor: ExecutorService// = Executors.newFixedThreadPool(threadCount)
|
||||
val futures = ArrayList<Future<*>>()
|
||||
private var isOpen = true
|
||||
|
||||
var allFinished = true
|
||||
private set
|
||||
|
||||
private fun checkShutdown() {
|
||||
try {
|
||||
if (executor.isTerminated)
|
||||
throw IllegalStateException("Executor terminated, renew the executor service.")
|
||||
if (!isOpen || executor.isShutdown)
|
||||
throw IllegalStateException("Pool is closed, come back when all the threads are terminated.")
|
||||
}
|
||||
catch (e: UninitializedPropertyAccessException) {}
|
||||
}
|
||||
|
||||
fun renew() {
|
||||
try {
|
||||
if (!executor.isTerminated && !executor.isShutdown) throw IllegalStateException("Pool is still running")
|
||||
}
|
||||
catch (_: UninitializedPropertyAccessException) {}
|
||||
|
||||
executor = Executors.newFixedThreadPool(threadCount)
|
||||
futures.clear()
|
||||
isOpen = true
|
||||
allFinished = false
|
||||
}
|
||||
|
||||
/*fun invokeAll(ts: List<Callable<Unit>>) {
|
||||
checkShutdown()
|
||||
executor.invokeAll(ts)
|
||||
}*/
|
||||
|
||||
fun submit(t: Callable<Unit>) {
|
||||
checkShutdown()
|
||||
futures.add(executor.submit(t))
|
||||
}
|
||||
fun submitAll(ts: List<Callable<Unit>>) {
|
||||
checkShutdown()
|
||||
ts.forEach { futures.add(executor.submit(it)) }
|
||||
}
|
||||
|
||||
// https://stackoverflow.com/questions/28818494/threads-stopping-prematurely-for-certain-values
|
||||
fun join() {
|
||||
//println("ThreadExecutor.join")
|
||||
isOpen = false
|
||||
futures.forEach {
|
||||
try {
|
||||
it.get()
|
||||
}
|
||||
catch (e: ExecutionException) {
|
||||
throw e
|
||||
}
|
||||
}
|
||||
executor.shutdown() // thread status of completed ones will be WAIT instead of TERMINATED without this line...
|
||||
executor.awaitTermination(24L, TimeUnit.HOURS)
|
||||
allFinished = true
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Shallow flat of the array
|
||||
*/
|
||||
fun <T> Array<out Iterable<T>>.flatten(): List<T> {
|
||||
val al = ArrayList<T>()
|
||||
this.forEach { it.forEach { al.add(it) } }
|
||||
return al
|
||||
}
|
||||
|
||||
/**
|
||||
* Shallow flat of the iterable
|
||||
*/
|
||||
fun <T> Iterable<out Iterable<T>>.flatten(): List<T> {
|
||||
val al = ArrayList<T>()
|
||||
this.forEach { it.forEach { al.add(it) } }
|
||||
return al
|
||||
}
|
||||
|
||||
/**
|
||||
* Shallow flat of the array
|
||||
*/
|
||||
fun <T> Array<out Array<T>>.flatten(): List<T> {
|
||||
val al = ArrayList<T>()
|
||||
this.forEach { it.forEach { al.add(it) } }
|
||||
return al
|
||||
}
|
||||
|
||||
fun <T> Iterable<T>.sliceEvenly(slices: Int): List<List<T>> = this.toList().sliceEvenly(slices)
|
||||
|
||||
fun <T> List<T>.sliceEvenly(slices: Int): List<List<T>> {
|
||||
return (0 until slices).map {
|
||||
this.subList(
|
||||
this.size.toFloat().div(slices).times(it).roundToInt(),
|
||||
this.size.toFloat().div(slices).times(it + 1).roundToInt()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
fun <T> Array<T>.sliceEvenly(slices: Int): List<Array<T>> {
|
||||
return (0 until slices).map {
|
||||
this.sliceArray(
|
||||
this.size.toFloat().div(slices).times(it).roundToInt() until
|
||||
this.size.toFloat().div(slices).times(it + 1).roundToInt()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
fun IntProgression.sliceEvenly(slices: Int): List<IntProgression> {
|
||||
if (this.step.absoluteValue != 1) throw UnsupportedOperationException("Sorry, step != +1/-1")
|
||||
val size = (this.last - this.first).absoluteValue + (this.step.toFloat()).absoluteValue
|
||||
|
||||
// println(size)
|
||||
|
||||
return if (this.first < this.last) (0 until slices).map {
|
||||
this.first + size.div(slices).times(it).roundToInt() ..
|
||||
this.first + size.div(slices).times(it + 1).roundToInt() - 1
|
||||
}
|
||||
else (0 until slices).map {
|
||||
this.first - size.div(slices).times(it).roundToInt() downTo
|
||||
this.first - size.div(slices).times(it + 1).roundToInt() + 1
|
||||
}
|
||||
}
|
||||
261
src/net/torvald/terrarum/concurrent/ThreadParallel.kt
Normal file
261
src/net/torvald/terrarum/concurrent/ThreadParallel.kt
Normal file
@@ -0,0 +1,261 @@
|
||||
package net.torvald.terrarum.concurrent
|
||||
|
||||
import java.util.concurrent.ExecutorService
|
||||
import java.util.concurrent.Executors
|
||||
import java.util.concurrent.Future
|
||||
import java.util.concurrent.TimeUnit
|
||||
import kotlin.math.absoluteValue
|
||||
|
||||
typealias RunnableFun = () -> Unit
|
||||
/** Int: index of the processing core */
|
||||
typealias ThreadableFun = (Int) -> Unit
|
||||
|
||||
|
||||
object ThreadExecutor {
|
||||
val threadCount = Runtime.getRuntime().availableProcessors() // not using (logicalCores + 1) method; it's often better idea to reserve one extra thread for other jobs in the app
|
||||
private lateinit var executor: ExecutorService// = Executors.newFixedThreadPool(threadCount)
|
||||
|
||||
private fun checkShutdown() {
|
||||
try {
|
||||
if (executor.isTerminated)
|
||||
throw IllegalStateException("Executor terminated, renew the executor service.")
|
||||
if (executor.isShutdown)
|
||||
throw IllegalStateException("Pool is closed, come back when all the threads are terminated.")
|
||||
}
|
||||
catch (e: UninitializedPropertyAccessException) {}
|
||||
}
|
||||
|
||||
fun renew() {
|
||||
executor = Executors.newFixedThreadPool(threadCount)
|
||||
}
|
||||
|
||||
fun submit(t: Runnable): Future<*> {
|
||||
checkShutdown()
|
||||
return executor.submit(t)
|
||||
}
|
||||
fun submit(f: RunnableFun): Future<*> {
|
||||
checkShutdown()
|
||||
return executor.submit { f() }
|
||||
}
|
||||
|
||||
fun join() {
|
||||
println("ThreadExecutor.join")
|
||||
executor.shutdown() // thread status of completed ones will be WAIT instead of TERMINATED without this line...
|
||||
executor.awaitTermination(24L, TimeUnit.HOURS)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-05-25.
|
||||
*/
|
||||
@Deprecated("Hooey implementation", ReplaceWith("ThreadExecutor", "net.torvald.terrarum.concurrent.ThreadExecutor"))
|
||||
object ThreadParallel {
|
||||
val threadCount = Runtime.getRuntime().availableProcessors() // not using (logicalCores + 1) method; it's often better idea to reserve one extra thread for other jobs in the app
|
||||
|
||||
private val pool: Array<Thread?> = Array(threadCount) { null }
|
||||
|
||||
/**
|
||||
* Map Runnable object to certain index of the thread pool.
|
||||
* @param index of the runnable
|
||||
* @param runnable
|
||||
* @param prefix Will name each thread like "Foo-1", "Foo-2", etc.
|
||||
*/
|
||||
fun map(index: Int, prefix: String, runnable: Runnable) {
|
||||
pool[index] = Thread(runnable, "$prefix-$index")
|
||||
}
|
||||
|
||||
/**
|
||||
* @param runFunc A function that takes an int input (the index), and returns nothing
|
||||
*/
|
||||
fun map(index: Int, prefix: String, runFunc: ThreadableFun) {
|
||||
val runnable = object : Runnable {
|
||||
override fun run() {
|
||||
runFunc(index)
|
||||
}
|
||||
}
|
||||
|
||||
map(index, prefix, runnable)
|
||||
}
|
||||
|
||||
/**
|
||||
* Start all thread in the pool. If the thread in the pool is NULL, it will simply ignored.
|
||||
*/
|
||||
fun startAll() {
|
||||
pool.forEach { it?.start() }
|
||||
}
|
||||
|
||||
/**
|
||||
* Start all thread in the pool and wait for them to all die. If the thread in the pool is NULL, it will simply ignored.
|
||||
*/
|
||||
fun startAllWaitForDie() {
|
||||
// ThreadParallelTester says this function actually works as intended...
|
||||
pool.forEach { it?.start() }
|
||||
pool.forEach { it?.join() }
|
||||
}
|
||||
|
||||
/**
|
||||
* Primitive locking
|
||||
*/
|
||||
fun allFinished(): Boolean {
|
||||
pool.forEach { if (it != null && it.state != Thread.State.TERMINATED) return false }
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* A thread pool that will hold the execution until all the tasks are completed.
|
||||
*
|
||||
* Tasks are not guaranteed to be done orderly; but the first task in the list will be executed first.
|
||||
*/
|
||||
@Deprecated("Experimental.", ReplaceWith("ThreadParallel", "net.torvald.terrarum.concurrent.ThreadParallel"))
|
||||
object BlockingThreadPool {
|
||||
val threadCount = Runtime.getRuntime().availableProcessors() + 1 // modify this to your taste
|
||||
private val pool: Array<Thread?> = Array(threadCount, { null })
|
||||
private var tasks: List<RunnableFun> = ArrayList<RunnableFun>()
|
||||
@Volatile private var dispatchedTasks = 0
|
||||
private var threadPrefix = ""
|
||||
|
||||
/** @return false on failure (likely the previous jobs not finished), true on success */
|
||||
fun map(prefix: String, tasks: List<RunnableFun>) = setTasks(tasks, prefix)
|
||||
/** @return false on failure (likely the previous jobs not finished), true on success */
|
||||
fun setTasks(tasks: List<RunnableFun>, prefix: String): Boolean {
|
||||
if (!allFinished())
|
||||
return false
|
||||
|
||||
this.tasks = tasks
|
||||
dispatchedTasks = 0
|
||||
threadPrefix = prefix
|
||||
return true
|
||||
}
|
||||
|
||||
private fun dequeueTask(): RunnableFun {
|
||||
dispatchedTasks += 1
|
||||
return tasks[dispatchedTasks - 1]
|
||||
}
|
||||
|
||||
|
||||
fun startAllWaitForDie() {
|
||||
while (dispatchedTasks <= tasks.lastIndex) {
|
||||
// marble rolling down the slanted channel-track of threads, if a channel is empty (a task assigned
|
||||
// to the thread is dead) the marble will roll into the channel, and the marble is a task #MarbleMachineX
|
||||
for (i in 0 until threadCount) {
|
||||
// but unlike the marble machine, marble don't actually roll down, we can just pick up any number
|
||||
// of marbles and put it into an empty channel whenever we encounter one
|
||||
|
||||
// SO WHAT WE DO is first fill any empty channels:
|
||||
if (dispatchedTasks <= tasks.lastIndex && // because cache invalidation damnit
|
||||
(pool[i] == null || pool[i]!!.state == Thread.State.TERMINATED)) {
|
||||
pool[i] = Thread(dequeueTask().makeRunnable(), "$threadPrefix-$dispatchedTasks") // thread name index is one-based
|
||||
pool[i]!!.start()
|
||||
}
|
||||
|
||||
// then, sleep this very thread, wake if any of the thread in the pool is terminated,
|
||||
// and GOTO loop_start; if we don't sleep, this function will be busy-waiting
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun allFinished(): Boolean {
|
||||
pool.forEach { if (it != null && it.state != Thread.State.TERMINATED) return false }
|
||||
return true
|
||||
}
|
||||
|
||||
|
||||
private fun RunnableFun.makeRunnable() = Runnable {
|
||||
this.invoke()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
fun <T, R> Iterable<T>.parallelMap(transform: (T) -> R): List<R> {
|
||||
val tasks = this.sliceEvenly(ThreadParallel.threadCount)
|
||||
val destination = Array(ThreadParallel.threadCount) { ArrayList<R>() }
|
||||
tasks.forEachIndexed { index, list ->
|
||||
ThreadParallel.map(index, "ParallelUtils.parallelMap@${this.javaClass.canonicalName}") {
|
||||
for (item in list)
|
||||
destination[index].add(transform(item as T))
|
||||
}
|
||||
}
|
||||
|
||||
ThreadParallel.startAllWaitForDie()
|
||||
|
||||
return destination.flatten()
|
||||
}
|
||||
|
||||
/**
|
||||
* Shallow flat of the array
|
||||
*/
|
||||
fun <T> Array<out Iterable<T>>.flatten(): List<T> {
|
||||
val al = ArrayList<T>()
|
||||
this.forEach { it.forEach { al.add(it) } }
|
||||
return al
|
||||
}
|
||||
|
||||
/**
|
||||
* Shallow flat of the iterable
|
||||
*/
|
||||
fun <T> Iterable<out Iterable<T>>.flatten(): List<T> {
|
||||
val al = ArrayList<T>()
|
||||
this.forEach { it.forEach { al.add(it) } }
|
||||
return al
|
||||
}
|
||||
|
||||
/**
|
||||
* Shallow flat of the array
|
||||
*/
|
||||
fun <T> Array<out Array<T>>.flatten(): List<T> {
|
||||
val al = ArrayList<T>()
|
||||
this.forEach { it.forEach { al.add(it) } }
|
||||
return al
|
||||
}
|
||||
|
||||
fun <T> Iterable<T>.sliceEvenly(slices: Int): List<List<T>> = this.toList().sliceEvenly(slices)
|
||||
|
||||
fun <T> List<T>.sliceEvenly(slices: Int): List<List<T>> {
|
||||
return (0 until slices).map {
|
||||
this.subList(
|
||||
this.size.toFloat().div(slices).times(it).roundInt(),
|
||||
this.size.toFloat().div(slices).times(it + 1).roundInt()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
fun <T> Array<T>.sliceEvenly(slices: Int): List<Array<T>> {
|
||||
return (0 until slices).map {
|
||||
this.sliceArray(
|
||||
this.size.toFloat().div(slices).times(it).roundInt() until
|
||||
this.size.toFloat().div(slices).times(it + 1).roundInt()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
fun IntProgression.sliceEvenly(slices: Int): List<IntProgression> {
|
||||
if (this.step.absoluteValue != 1) throw UnsupportedOperationException("Sorry, step != +1/-1")
|
||||
val size = (this.last - this.first).absoluteValue + (this.step.toFloat()).absoluteValue
|
||||
|
||||
// println(size)
|
||||
|
||||
return if (this.first < this.last) (0 until slices).map {
|
||||
this.first + size.div(slices).times(it).roundInt() ..
|
||||
this.first + size.div(slices).times(it + 1).roundInt() - 1
|
||||
}
|
||||
else (0 until slices).map {
|
||||
this.first - size.div(slices).times(it).roundInt() downTo
|
||||
this.first - size.div(slices).times(it + 1).roundInt() + 1
|
||||
}
|
||||
}
|
||||
|
||||
fun IntProgression.mapToThreadPoolDirectly(prefix: String, worker: (IntProgression) -> Unit) {
|
||||
this.sliceEvenly(ThreadParallel.threadCount).forEachIndexed { index, intProgression ->
|
||||
val workerFun: ThreadableFun = {
|
||||
worker(intProgression)
|
||||
}
|
||||
ThreadParallel.map(index, prefix, workerFun)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private inline fun Float.roundInt(): Int = Math.round(this)
|
||||
@@ -26,7 +26,7 @@ internal object SetGlobalLightOverride : ConsoleCommand {
|
||||
Echo("Wrong number input.")
|
||||
}
|
||||
catch (e1: IllegalArgumentException) {
|
||||
Echo("Range: 0.0-1.0+ per channel")
|
||||
Echo("Range: 0-" + LightmapRenderer.CHANNEL_MAX + " per channel")
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -10,7 +10,6 @@ import net.torvald.terrarum.blockproperties.Block
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.blockproperties.BlockProp
|
||||
import net.torvald.terrarum.gamecontroller.KeyToggler
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.BlockAddress
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.ActorHumanoid
|
||||
@@ -21,7 +20,6 @@ import net.torvald.terrarumsansbitmap.gdx.TextureRegionPack
|
||||
import org.dyn4j.geometry.Vector2
|
||||
import java.util.*
|
||||
import kotlin.math.absoluteValue
|
||||
import kotlin.math.roundToInt
|
||||
import kotlin.math.sign
|
||||
|
||||
|
||||
@@ -1232,7 +1230,7 @@ open class ActorWithBody(renderOrder: RenderOrder, val physProp: PhysProperties)
|
||||
*
|
||||
* Very straightforward for the actual solid tiles, not so much for the platforms
|
||||
*/
|
||||
private fun shouldICollideWithThis(tile: ItemID) =
|
||||
private fun shouldICollideWithThis(tile: Int) =
|
||||
// regular solid block
|
||||
(BlockCodex[tile].isSolid)
|
||||
|
||||
@@ -1241,7 +1239,7 @@ open class ActorWithBody(renderOrder: RenderOrder, val physProp: PhysProperties)
|
||||
*
|
||||
* Just like "shouldICollideWithThis" but it's intended to work with feet tiles
|
||||
*/
|
||||
private fun shouldICollideWithThisFeet(tile: ItemID) =
|
||||
private fun shouldICollideWithThisFeet(tile: Int) =
|
||||
// regular solid block
|
||||
(BlockCodex[tile].isSolid) ||
|
||||
// platforms, moving downward AND not "going down"
|
||||
@@ -1259,28 +1257,28 @@ open class ActorWithBody(renderOrder: RenderOrder, val physProp: PhysProperties)
|
||||
if (world == null) return 0
|
||||
|
||||
var contactAreaCounter = 0
|
||||
for (i in 0..(if (side % 2 == 0) hitbox.width else hitbox.height).roundToInt() - 1) {
|
||||
for (i in 0..(if (side % 2 == 0) hitbox.width else hitbox.height).roundInt() - 1) {
|
||||
// set tile positions
|
||||
val tileX: Int
|
||||
val tileY: Int
|
||||
if (side == COLLIDING_LEFT) {
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxStart.x.roundToInt()
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxStart.x.roundInt()
|
||||
+ i + translateX)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxEnd.y.roundToInt() + translateY)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxEnd.y.roundInt() + translateY)
|
||||
}
|
||||
else if (side == COLLIDING_TOP) {
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxStart.x.roundToInt()
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxStart.x.roundInt()
|
||||
+ i + translateX)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxStart.y.roundToInt() + translateY)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxStart.y.roundInt() + translateY)
|
||||
}
|
||||
else if (side == COLLIDING_RIGHT) {
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxEnd.x.roundToInt() + translateX)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxStart.y.roundToInt()
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxEnd.x.roundInt() + translateX)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxStart.y.roundInt()
|
||||
+ i + translateY)
|
||||
}
|
||||
else if (side == COLLIDING_LEFT) {
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxStart.x.roundToInt() + translateX)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxStart.y.roundToInt()
|
||||
tileX = div16TruncateToMapWidth(hitbox.hitboxStart.x.roundInt() + translateX)
|
||||
tileY = div16TruncateToMapHeight(hitbox.hitboxStart.y.roundInt()
|
||||
+ i + translateY)
|
||||
}
|
||||
else {
|
||||
@@ -1296,7 +1294,7 @@ open class ActorWithBody(renderOrder: RenderOrder, val physProp: PhysProperties)
|
||||
return contactAreaCounter
|
||||
}
|
||||
|
||||
private fun getTileFriction(tile: ItemID) =
|
||||
private fun getTileFriction(tile: Int) =
|
||||
if (physProp.immobileBody && tile == Block.AIR)
|
||||
BlockCodex[Block.AIR].friction.frictionToMult().div(500)
|
||||
.times(if (!grounded) elasticity else 1.0)
|
||||
@@ -1706,11 +1704,11 @@ open class ActorWithBody(renderOrder: RenderOrder, val physProp: PhysProperties)
|
||||
}
|
||||
|
||||
|
||||
private fun forEachOccupyingTileNum(consumer: (ItemID?) -> Unit) {
|
||||
private fun forEachOccupyingTileNum(consumer: (Int?) -> Unit) {
|
||||
if (world == null) return
|
||||
|
||||
|
||||
val tiles = ArrayList<ItemID?>()
|
||||
val tiles = ArrayList<Int?>()
|
||||
for (y in hIntTilewiseHitbox.startY.toInt()..hIntTilewiseHitbox.endY.toInt()) {
|
||||
for (x in hIntTilewiseHitbox.startX.toInt()..hIntTilewiseHitbox.endX.toInt()) {
|
||||
tiles.add(world!!.getTileFromTerrain(x, y))
|
||||
@@ -1771,11 +1769,11 @@ open class ActorWithBody(renderOrder: RenderOrder, val physProp: PhysProperties)
|
||||
return tilePosList.forEach(consumer)
|
||||
}
|
||||
|
||||
private fun forEachFeetTileNum(consumer: (ItemID?) -> Unit) {
|
||||
private fun forEachFeetTileNum(consumer: (Int?) -> Unit) {
|
||||
if (world == null) return
|
||||
|
||||
|
||||
val tiles = ArrayList<ItemID?>()
|
||||
val tiles = ArrayList<Int?>()
|
||||
|
||||
// offset 1 pixel to the down so that friction would work
|
||||
val y = hitbox.endY.plus(1.0).div(TILE_SIZE).floorInt()
|
||||
|
||||
@@ -46,8 +46,6 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
}
|
||||
}
|
||||
|
||||
private var worldPrimaryClickLatched = false
|
||||
|
||||
fun update(delta: Float) {
|
||||
|
||||
///////////////////
|
||||
@@ -63,18 +61,13 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
// also, some UIs should NOT affect item usage (e.g. quickslot) and ingame's uiOpened property is doing
|
||||
// the very job.
|
||||
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary")) && !worldPrimaryClickLatched) {
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("mouseprimary"))) {
|
||||
terrarumIngame.worldPrimaryClickStart(AppLoader.UPDATE_RATE)
|
||||
worldPrimaryClickLatched = true
|
||||
}
|
||||
/*if Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mousesecondary")) {
|
||||
/*if Gdx.input.isButtonPressed(AppLoader.getConfigInt("mousesecondary")) {
|
||||
ingame.worldSecondaryClickStart(AppLoader.UPDATE_RATE)
|
||||
}*/
|
||||
|
||||
if (!Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary"))) {
|
||||
worldPrimaryClickLatched = false
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -100,14 +93,14 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
terrarumIngame.actorNowPlaying?.keyDown(keycode)
|
||||
|
||||
// quickslot by number keys
|
||||
val quickslotKeys = AppLoader.getConfigIntArray("config_keyquickslots")
|
||||
val quickslotKeys = AppLoader.getConfigIntArray("keyquickslots")
|
||||
if (keycode in quickslotKeys) {
|
||||
terrarumIngame.actorNowPlaying?.actorValue?.set(AVKey.__PLAYER_QUICKSLOTSEL, quickslotKeys.indexOf(keycode))
|
||||
}
|
||||
|
||||
// pie menu
|
||||
if (AppLoader.getConfigIntArray("config_keyquickselalt").contains(keycode)
|
||||
|| keycode == AppLoader.getConfigInt("config_keyquicksel")) {
|
||||
if (AppLoader.getConfigIntArray("keyquickselalt").contains(keycode)
|
||||
|| keycode == AppLoader.getConfigInt("keyquicksel")) {
|
||||
terrarumIngame.uiPieMenu.setAsOpen()
|
||||
terrarumIngame.uiQuickBar.setAsClose()
|
||||
}
|
||||
@@ -124,6 +117,7 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
// screenshot key
|
||||
if (keycode == Input.Keys.F12 && !f12Down) {
|
||||
AppLoader.requestScreenshot()
|
||||
terrarumIngame.sendNotification("Screenshot taken")
|
||||
f12Down = true
|
||||
println("Screenshot taken.")
|
||||
}
|
||||
@@ -132,8 +126,8 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
}
|
||||
|
||||
override fun keyUp(keycode: Int): Boolean {
|
||||
if (AppLoader.getConfigIntArray("config_keyquickselalt").contains(keycode)
|
||||
|| keycode == AppLoader.getConfigInt("config_keyquicksel")) {
|
||||
if (AppLoader.getConfigIntArray("keyquickselalt").contains(keycode)
|
||||
|| keycode == AppLoader.getConfigInt("keyquicksel")) {
|
||||
terrarumIngame.uiPieMenu.setAsClose()
|
||||
terrarumIngame.uiQuickBar.setAsOpen()
|
||||
}
|
||||
@@ -165,18 +159,18 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
if (terrarumIngame.uiContainer.map { if ((it.isOpening || it.isOpened) && it.mouseUp) 1 else 0 }.sum() == 0) { // no UI on the mouse, right?
|
||||
|
||||
if (
|
||||
button == AppLoader.getConfigInt("config_mouseprimary") ||
|
||||
button == AppLoader.getConfigInt("config_mousesecondary")) {
|
||||
button == AppLoader.getConfigInt("mouseprimary") ||
|
||||
button == AppLoader.getConfigInt("mousesecondary")) {
|
||||
terrarumIngame.worldPrimaryClickEnd(AppLoader.UPDATE_RATE)
|
||||
}
|
||||
/*if (button == AppLoader.getConfigInt("config_mousesecondary")) {
|
||||
/*if (button == AppLoader.getConfigInt("mousesecondary")) {
|
||||
ingame.worldSecondaryClickEnd(AppLoader.UPDATE_RATE)
|
||||
}*/
|
||||
}
|
||||
}
|
||||
|
||||
// pie menu
|
||||
if (button == AppLoader.getConfigInt("config_mousequicksel")) {
|
||||
if (button == AppLoader.getConfigInt("mousequicksel")) {
|
||||
terrarumIngame.uiPieMenu.setAsClose()
|
||||
terrarumIngame.uiQuickBar.setAsOpen()
|
||||
}
|
||||
@@ -210,7 +204,7 @@ class IngameController(val terrarumIngame: TerrarumIngame) : InputAdapter() {
|
||||
terrarumIngame.uiContainer.forEach { it.touchDown(screenX, screenY, pointer, button) }
|
||||
|
||||
// pie menu
|
||||
if (button == AppLoader.getConfigInt("config_mousequicksel")) {
|
||||
if (button == AppLoader.getConfigInt("mousequicksel")) {
|
||||
terrarumIngame.uiPieMenu.setAsOpen()
|
||||
terrarumIngame.uiQuickBar.setAsClose()
|
||||
}
|
||||
|
||||
@@ -4,14 +4,14 @@ import com.badlogic.gdx.graphics.Color
|
||||
import com.badlogic.gdx.graphics.g2d.TextureRegion
|
||||
import net.torvald.random.HQRNG
|
||||
import net.torvald.terrarum.ItemValue
|
||||
import net.torvald.terrarum.ReferencingRanges.PREFIX_DYNAMICITEM
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex.ITEM_DYNAMIC
|
||||
import net.torvald.terrarum.itemproperties.Material
|
||||
import net.torvald.terrarum.langpack.Lang
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.ActorInventory
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.Pocketed
|
||||
|
||||
typealias ItemID = String
|
||||
typealias ItemID = Int
|
||||
|
||||
/**
|
||||
* Instances of the GameItem (e.g. net.torvald.terrarum.modulebasegame.gameitems.PickaxeCopper) are preferably referenced
|
||||
@@ -40,7 +40,7 @@ abstract class GameItem(val originalID: ItemID) : Comparable<GameItem>, Cloneabl
|
||||
abstract val originalName: String
|
||||
|
||||
|
||||
var newName: String = "I AM VITUN PLACEHOLDER"
|
||||
var newName: String = "I AM VITTUN PLACEHOLDER"
|
||||
private set
|
||||
|
||||
var name: String
|
||||
@@ -208,7 +208,7 @@ abstract class GameItem(val originalID: ItemID) : Comparable<GameItem>, Cloneabl
|
||||
}
|
||||
|
||||
override fun hashCode(): Int {
|
||||
return dynamicID.hashCode()
|
||||
return dynamicID
|
||||
}
|
||||
|
||||
override fun equals(other: Any?): Boolean {
|
||||
@@ -222,7 +222,7 @@ abstract class GameItem(val originalID: ItemID) : Comparable<GameItem>, Cloneabl
|
||||
nameColour = Color.WHITE
|
||||
}
|
||||
|
||||
override fun compareTo(other: GameItem): Int = (this.dynamicID.substring(4).toInt() - other.dynamicID.substring(4).toInt()).sign()
|
||||
override fun compareTo(other: GameItem): Int = (this.dynamicID - other.dynamicID).sign()
|
||||
|
||||
fun Int.sign(): Int = if (this > 0) 1 else if (this < 0) -1 else 0
|
||||
|
||||
@@ -295,7 +295,7 @@ abstract class GameItem(val originalID: ItemID) : Comparable<GameItem>, Cloneabl
|
||||
|
||||
|
||||
fun generateUniqueDynamicID(inventory: ActorInventory): GameItem {
|
||||
dynamicID = "$PREFIX_DYNAMICITEM${Companion.generateUniqueDynamicID(inventory)}"
|
||||
dynamicID = Companion.generateUniqueDynamicID(inventory)
|
||||
ItemCodex.registerNewDynamicItem(dynamicID, this)
|
||||
return this
|
||||
}
|
||||
@@ -307,8 +307,8 @@ abstract class GameItem(val originalID: ItemID) : Comparable<GameItem>, Cloneabl
|
||||
fun generateUniqueDynamicID(inventory: ActorInventory): Int {
|
||||
var ret: Int
|
||||
do {
|
||||
ret = (1..2147483647).pickRandom()
|
||||
} while (inventory.contains("$PREFIX_DYNAMICITEM$ret"))
|
||||
ret = ITEM_DYNAMIC.pickRandom()
|
||||
} while (inventory.contains(ret))
|
||||
|
||||
return ret
|
||||
}
|
||||
|
||||
@@ -9,12 +9,10 @@ import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.blockproperties.Block
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.blockproperties.Fluid
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.modulebasegame.gameworld.WorldSimulator
|
||||
import net.torvald.terrarum.printStackTrace
|
||||
import net.torvald.terrarum.realestate.LandUtil
|
||||
import net.torvald.terrarum.serialise.ReadLayerDataZip
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||
import net.torvald.util.SortedArrayList
|
||||
import org.dyn4j.geometry.Vector2
|
||||
import kotlin.math.absoluteValue
|
||||
@@ -81,7 +79,7 @@ open class GameWorld : Disposable {
|
||||
/**
|
||||
* Used by the renderer. When wirings are updated, `wirings` and this properties must be synchronised.
|
||||
*/
|
||||
private val wiringBlocks: HashMap<BlockAddress, ItemID>
|
||||
private val wiringBlocks: HashMap<BlockAddress, Int>
|
||||
|
||||
//public World physWorld = new World( new Vec2(0, -Terrarum.game.gravitationalAccel) );
|
||||
//physics
|
||||
@@ -102,14 +100,7 @@ open class GameWorld : Disposable {
|
||||
open var TIME_T: Long = 0L
|
||||
open var dayLength: Int = 86400
|
||||
|
||||
@TEMzPayload("TMaP", TEMzPayload.EXTERNAL_JSON)
|
||||
val tileNumberToNameMap: HashMap<Int, ItemID>
|
||||
// does not go to the savefile
|
||||
val tileNameToNumberMap: HashMap<ItemID, Int>
|
||||
|
||||
/**
|
||||
* Create new world
|
||||
*/
|
||||
constructor(worldIndex: Int, width: Int, height: Int, creationTIME_T: Long, lastPlayTIME_T: Long, totalPlayTime: Int) {
|
||||
if (width <= 0 || height <= 0) throw IllegalArgumentException("Non-positive width/height: ($width, $height)")
|
||||
|
||||
@@ -142,24 +133,8 @@ open class GameWorld : Disposable {
|
||||
creationTime = creationTIME_T
|
||||
lastPlayTime = lastPlayTIME_T
|
||||
this.totalPlayTime = totalPlayTime
|
||||
|
||||
|
||||
tileNumberToNameMap = HashMap<Int, ItemID>()
|
||||
tileNameToNumberMap = HashMap<ItemID, Int>()
|
||||
CreateTileAtlas.tags.forEach {
|
||||
printdbg(this, "tileNumber ${it.value.tileNumber} <-> tileName ${it.key}")
|
||||
|
||||
tileNumberToNameMap[it.value.tileNumber] = it.key
|
||||
tileNameToNumberMap[it.key] = it.value.tileNumber
|
||||
}
|
||||
|
||||
// AN EXCEPTIONAL TERM: tilenum 0 is always redirected to Air tile, even if the tilenum for actual Air tile is not zero
|
||||
tileNumberToNameMap[0] = Block.AIR
|
||||
}
|
||||
|
||||
/**
|
||||
* Load existing world
|
||||
*/
|
||||
internal constructor(worldIndex: Int, layerData: ReadLayerDataZip.LayerData, creationTIME_T: Long, lastPlayTIME_T: Long, totalPlayTime: Int) {
|
||||
this.worldIndex = worldIndex
|
||||
|
||||
@@ -185,28 +160,6 @@ open class GameWorld : Disposable {
|
||||
creationTime = creationTIME_T
|
||||
lastPlayTime = lastPlayTIME_T
|
||||
this.totalPlayTime = totalPlayTime
|
||||
|
||||
// before the renaming, update the name maps
|
||||
tileNumberToNameMap = HashMap<Int, ItemID>()
|
||||
tileNameToNumberMap = HashMap<ItemID, Int>()
|
||||
CreateTileAtlas.tags.forEach {
|
||||
tileNumberToNameMap[it.value.tileNumber] = it.key
|
||||
tileNameToNumberMap[it.key] = it.value.tileNumber
|
||||
}
|
||||
|
||||
// perform renaming of tile layers
|
||||
val oldTileNumberToNameMap = layerData.tileNumberToNameMap
|
||||
for (y in 0 until layerTerrain.height) {
|
||||
for (x in 0 until layerTerrain.width) {
|
||||
layerTerrain.unsafeSetTile(x, y, tileNameToNumberMap[oldTileNumberToNameMap[layerTerrain.unsafeGetTile(x, y)]]!!)
|
||||
layerWall.unsafeSetTile(x, y, tileNameToNumberMap[oldTileNumberToNameMap[layerWall.unsafeGetTile(x, y)]]!!)
|
||||
// TODO rename fluid map
|
||||
// TODO rename wire map
|
||||
}
|
||||
}
|
||||
|
||||
// AN EXCEPTIONAL TERM: tilenum 0 is always redirected to Air tile, even if the tilenum for actual Air tile is not zero
|
||||
tileNumberToNameMap[0] = Block.AIR
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -219,41 +172,12 @@ open class GameWorld : Disposable {
|
||||
|
||||
fun coerceXY(x: Int, y: Int) = (x fmod width) to (y.coerceIn(0, height - 1))
|
||||
|
||||
/**
|
||||
* @return ItemID, WITHOUT wall tag
|
||||
*/
|
||||
fun getTileFromWall(rawX: Int, rawY: Int): ItemID {
|
||||
val (x, y) = coerceXY(rawX, rawY)
|
||||
return tileNumberToNameMap[layerWall.unsafeGetTile(x, y)]!!
|
||||
}
|
||||
|
||||
/**
|
||||
* @return ItemID
|
||||
*/
|
||||
fun getTileFromTerrain(rawX: Int, rawY: Int): ItemID {
|
||||
val (x, y) = coerceXY(rawX, rawY)
|
||||
|
||||
try {
|
||||
return tileNumberToNameMap[layerTerrain.unsafeGetTile(x, y)]!!
|
||||
}
|
||||
catch (e: NullPointerException) {
|
||||
System.err.println("NPE for tilenum ${layerTerrain.unsafeGetTile(x, y)}")
|
||||
throw e
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return Int
|
||||
*/
|
||||
fun getTileNumFromWall(rawX: Int, rawY: Int): Int {
|
||||
fun getTileFromWall(rawX: Int, rawY: Int): Int {
|
||||
val (x, y) = coerceXY(rawX, rawY)
|
||||
return layerWall.unsafeGetTile(x, y)
|
||||
}
|
||||
|
||||
/**
|
||||
* @return Int
|
||||
*/
|
||||
fun getTileNumFromTerrain(rawX: Int, rawY: Int): Int {
|
||||
fun getTileFromTerrain(rawX: Int, rawY: Int): Int {
|
||||
val (x, y) = coerceXY(rawX, rawY)
|
||||
return layerTerrain.unsafeGetTile(x, y)
|
||||
}
|
||||
@@ -267,18 +191,17 @@ open class GameWorld : Disposable {
|
||||
* *
|
||||
* @param y
|
||||
* *
|
||||
* @param itemID Tile as in ItemID, with tag removed!
|
||||
* @param tilenum Item id of the wall block. Less-than-4096-value is permitted.
|
||||
*/
|
||||
fun setTileWall(x: Int, y: Int, itemID: ItemID, bypassEvent: Boolean) {
|
||||
fun setTileWall(x: Int, y: Int, tilenum: Int) {
|
||||
val (x, y) = coerceXY(x, y)
|
||||
val tilenum = tileNameToNumberMap[itemID]!!
|
||||
val tilenum = tilenum % TILES_SUPPORTED // does work without this, but to be safe...
|
||||
|
||||
val oldWall = getTileFromWall(x, y)
|
||||
layerWall.unsafeSetTile(x, y, tilenum)
|
||||
wallDamages.remove(LandUtil.getBlockAddr(this, x, y))
|
||||
|
||||
if (!bypassEvent)
|
||||
Terrarum.ingame?.queueWallChangedEvent(oldWall, itemID, LandUtil.getBlockAddr(this, x, y))
|
||||
Terrarum.ingame?.queueWallChangedEvent(oldWall, tilenum, LandUtil.getBlockAddr(this, x, y))
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -290,25 +213,23 @@ open class GameWorld : Disposable {
|
||||
* *
|
||||
* @param y
|
||||
* *
|
||||
* @param itemID Tile as in ItemID, with tag removed!
|
||||
* @param tilenum Item id of the terrain block, <4096
|
||||
*/
|
||||
fun setTileTerrain(x: Int, y: Int, itemID: ItemID, bypassEvent: Boolean) {
|
||||
fun setTileTerrain(x: Int, y: Int, tilenum: Int) {
|
||||
val (x, y) = coerceXY(x, y)
|
||||
val tilenum = tileNameToNumberMap[itemID]!!
|
||||
|
||||
val oldTerrain = getTileFromTerrain(x, y)
|
||||
layerTerrain.unsafeSetTile(x, y, tilenum)
|
||||
val blockAddr = LandUtil.getBlockAddr(this, x, y)
|
||||
terrainDamages.remove(blockAddr)
|
||||
|
||||
if (BlockCodex[itemID].isSolid) {
|
||||
if (BlockCodex[tilenum].isSolid) {
|
||||
fluidFills.remove(blockAddr)
|
||||
fluidTypes.remove(blockAddr)
|
||||
}
|
||||
// fluid tiles-item should be modified so that they will also place fluid onto their respective map
|
||||
|
||||
if (!bypassEvent)
|
||||
Terrarum.ingame?.queueTerrainChangedEvent(oldTerrain, itemID, LandUtil.getBlockAddr(this, x, y))
|
||||
Terrarum.ingame?.queueTerrainChangedEvent(oldTerrain, tilenum, LandUtil.getBlockAddr(this, x, y))
|
||||
}
|
||||
|
||||
/*fun setTileWire(x: Int, y: Int, tile: Byte) {
|
||||
@@ -320,9 +241,8 @@ open class GameWorld : Disposable {
|
||||
Terrarum.ingame?.queueWireChangedEvent(oldWire, tile.toUint(), LandUtil.getBlockAddr(this, x, y))
|
||||
}*/
|
||||
|
||||
fun getWiringBlocks(x: Int, y: Int): ItemID {
|
||||
return Block.AIR // TODO
|
||||
//return wiringBlocks.getOrDefault(LandUtil.getBlockAddr(this, x, y), Block.AIR)
|
||||
fun getWiringBlocks(x: Int, y: Int): Int {
|
||||
return wiringBlocks.getOrDefault(LandUtil.getBlockAddr(this, x, y), 0)
|
||||
}
|
||||
|
||||
fun getAllConduitsFrom(x: Int, y: Int): SortedArrayList<WiringNode>? {
|
||||
@@ -338,9 +258,7 @@ open class GameWorld : Disposable {
|
||||
}
|
||||
|
||||
fun addNewConduitTo(x: Int, y: Int, node: WiringNode) {
|
||||
// TODO needs new conduit storage scheme
|
||||
|
||||
/*val blockAddr = LandUtil.getBlockAddr(this, x, y)
|
||||
val blockAddr = LandUtil.getBlockAddr(this, x, y)
|
||||
|
||||
// check for existing type of conduit
|
||||
// if there's no duplicate...
|
||||
@@ -352,10 +270,10 @@ open class GameWorld : Disposable {
|
||||
}
|
||||
else {
|
||||
TODO("need overwriting policy for existing conduit node")
|
||||
}*/
|
||||
}
|
||||
}
|
||||
|
||||
fun getTileFrom(mode: Int, x: Int, y: Int): ItemID {
|
||||
fun getTileFrom(mode: Int, x: Int, y: Int): Int? {
|
||||
if (mode == TERRAIN) {
|
||||
return getTileFromTerrain(x, y)
|
||||
}
|
||||
@@ -369,8 +287,8 @@ open class GameWorld : Disposable {
|
||||
throw IllegalArgumentException("illegal mode input: " + mode.toString())
|
||||
}
|
||||
|
||||
fun terrainIterator(): Iterator<ItemID> {
|
||||
return object : Iterator<ItemID> {
|
||||
fun terrainIterator(): Iterator<Int> {
|
||||
return object : Iterator<Int> {
|
||||
|
||||
private var iteratorCount = 0
|
||||
|
||||
@@ -378,7 +296,7 @@ open class GameWorld : Disposable {
|
||||
return iteratorCount < width * height
|
||||
}
|
||||
|
||||
override fun next(): ItemID {
|
||||
override fun next(): Int {
|
||||
val y = iteratorCount / width
|
||||
val x = iteratorCount % width
|
||||
// advance counter
|
||||
@@ -390,15 +308,15 @@ open class GameWorld : Disposable {
|
||||
}
|
||||
}
|
||||
|
||||
fun wallIterator(): Iterator<ItemID> {
|
||||
return object : Iterator<ItemID> {
|
||||
fun wallIterator(): Iterator<Int> {
|
||||
return object : Iterator<Int> {
|
||||
|
||||
private var iteratorCount = 0
|
||||
|
||||
override fun hasNext(): Boolean =
|
||||
iteratorCount < width * height
|
||||
|
||||
override fun next(): ItemID {
|
||||
override fun next(): Int {
|
||||
val y = iteratorCount / width
|
||||
val x = iteratorCount % width
|
||||
// advance counter
|
||||
@@ -433,7 +351,7 @@ open class GameWorld : Disposable {
|
||||
|
||||
// remove tile from the world
|
||||
if (terrainDamages[addr] ?: 0f >= BlockCodex[getTileFromTerrain(x, y)].strength) {
|
||||
setTileTerrain(x, y, Block.AIR, false)
|
||||
setTileTerrain(x, y, 0)
|
||||
terrainDamages.remove(addr)
|
||||
return true
|
||||
}
|
||||
@@ -462,7 +380,7 @@ open class GameWorld : Disposable {
|
||||
|
||||
// remove tile from the world
|
||||
if (wallDamages[addr]!! >= BlockCodex[getTileFromWall(x, y)].strength) {
|
||||
setTileWall(x, y, Block.AIR, false)
|
||||
setTileWall(x, y, 0)
|
||||
wallDamages.remove(addr)
|
||||
return true
|
||||
}
|
||||
|
||||
@@ -5,11 +5,7 @@ import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.CommonResourcePool
|
||||
import net.torvald.terrarum.ReferencingRanges
|
||||
import net.torvald.terrarum.ReferencingRanges.PREFIX_ACTORITEM
|
||||
import net.torvald.terrarum.ReferencingRanges.PREFIX_DYNAMICITEM
|
||||
import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.blockproperties.BlockProp
|
||||
import net.torvald.terrarum.blockproperties.Fluid
|
||||
import net.torvald.terrarum.gameitem.GameItem
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
@@ -17,8 +13,6 @@ import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.CanBeAnItem
|
||||
import net.torvald.terrarum.worlddrawer.BlocksDrawer
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas.ITEM_ATLAS_TILES_X
|
||||
import java.util.*
|
||||
|
||||
/**
|
||||
@@ -30,19 +24,219 @@ object ItemCodex {
|
||||
* <ItemID or RefID for Actor, TheItem>
|
||||
* Will return corresponding Actor if ID >= ACTORID_MIN
|
||||
*/
|
||||
private val itemCodex = HashMap<ItemID, GameItem>()
|
||||
val itemCodex = HashMap<ItemID, GameItem>()
|
||||
val dynamicItemDescription = HashMap<ItemID, GameItem>()
|
||||
val dynamicToStaticTable = HashMap<ItemID, ItemID>()
|
||||
|
||||
val ITEM_TILES = ReferencingRanges.TILES
|
||||
val ITEM_WALLS = ReferencingRanges.WALLS
|
||||
val ITEM_WIRES = ReferencingRanges.WIRES
|
||||
val ITEM_STATIC = ReferencingRanges.ITEMS_STATIC
|
||||
val ITEM_DYNAMIC = ReferencingRanges.ITEMS_DYNAMIC
|
||||
val ACTORID_MIN = ReferencingRanges.ACTORS.first
|
||||
|
||||
private val itemImagePlaceholder: TextureRegion
|
||||
get() = CommonResourcePool.getAsTextureRegion("itemplaceholder_24") // copper pickaxe
|
||||
|
||||
/**
|
||||
* @param: dynamicID string of "dyn:<random id>"
|
||||
*/
|
||||
fun registerNewDynamicItem(dynamicID: ItemID, item: GameItem) {
|
||||
|
||||
// TODO: when generalised, there's no guarantee that blocks will be used as an item. Write customised item prop loader and init it on the Ingame
|
||||
|
||||
init {
|
||||
//val ingame = Terrarum.ingame!! as Ingame // WARNING you can't put this here, ExceptionInInitializerError
|
||||
|
||||
|
||||
/*println("[ItemCodex] recording item ID ")
|
||||
|
||||
// blocks.csvs are loaded by ModMgr beforehand
|
||||
// block items (blocks and walls are the same thing basically)
|
||||
for (i in ITEM_TILES + ITEM_WALLS) {
|
||||
itemCodex[i] = object : GameItem() {
|
||||
override val originalID = i
|
||||
override var dynamicID = i
|
||||
override val isUnique: Boolean = false
|
||||
override var baseMass: Double = BlockCodex[i].density / 1000.0
|
||||
override var baseToolSize: Double? = null
|
||||
override var equipPosition = EquipPosition.HAND_GRIP
|
||||
override val originalName = BlockCodex[i % ITEM_WALLS.first].nameKey
|
||||
override var stackable = true
|
||||
override var inventoryCategory = if (i in ITEM_TILES) Category.BLOCK else Category.WALL
|
||||
override var isDynamic = false
|
||||
override val material = Material(0,0,0,0,0,0,0,0,0,0.0)
|
||||
|
||||
init {
|
||||
print("$originalID ")
|
||||
}
|
||||
|
||||
override fun startPrimaryUse(delta: Float): Boolean {
|
||||
return false
|
||||
// TODO base punch attack
|
||||
}
|
||||
|
||||
override fun startSecondaryUse(delta: Float): Boolean {
|
||||
val mousePoint = Point2d(Terrarum.mouseTileX.toDouble(), Terrarum.mouseTileY.toDouble())
|
||||
|
||||
// check for collision with actors (BLOCK only)
|
||||
if (this.inventoryCategory == Category.BLOCK) {
|
||||
ingame.actorContainerActive.forEach {
|
||||
if (it is ActorWBMovable && it.hIntTilewiseHitbox.intersects(mousePoint))
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
// return false if the tile is already there
|
||||
if (this.inventoryCategory == Category.BLOCK &&
|
||||
this.dynamicID == ingame.world.getTileFromTerrain(Terrarum.mouseTileX, Terrarum.mouseTileY) ||
|
||||
this.inventoryCategory == Category.WALL &&
|
||||
this.dynamicID - ITEM_WALLS.start == ingame.world.getTileFromWall(Terrarum.mouseTileX, Terrarum.mouseTileY) ||
|
||||
this.inventoryCategory == Category.WIRE &&
|
||||
this.dynamicID - ITEM_WIRES.start == ingame.world.getTileFromWire(Terrarum.mouseTileX, Terrarum.mouseTileY)
|
||||
)
|
||||
return false
|
||||
|
||||
// filter passed, do the job
|
||||
// FIXME this is only useful for Player
|
||||
if (i in ITEM_TILES) {
|
||||
ingame.world.setTileTerrain(
|
||||
Terrarum.mouseTileX,
|
||||
Terrarum.mouseTileY,
|
||||
i
|
||||
)
|
||||
}
|
||||
else {
|
||||
ingame.world.setTileWall(
|
||||
Terrarum.mouseTileX,
|
||||
Terrarum.mouseTileY,
|
||||
i
|
||||
)
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
}
|
||||
}*/
|
||||
|
||||
// test copper pickaxe
|
||||
/*itemCodex[ITEM_STATIC.first] = object : GameItem() {
|
||||
override val originalID = ITEM_STATIC.first
|
||||
override var dynamicID = originalID
|
||||
override val isUnique = false
|
||||
override val originalName = ""
|
||||
override var baseMass = 10.0
|
||||
override var baseToolSize: Double? = 10.0
|
||||
override var stackable = true
|
||||
override var maxDurability = 147//606
|
||||
override var durability = maxDurability.toFloat()
|
||||
override var equipPosition = EquipPosition.HAND_GRIP
|
||||
override var inventoryCategory = Category.TOOL
|
||||
override val isDynamic = true
|
||||
override val material = Material(0,0,0,0,0,0,0,0,1,0.0)
|
||||
|
||||
init {
|
||||
itemProperties[IVKey.ITEMTYPE] = IVKey.ItemType.PICK
|
||||
name = "Stone pickaxe"
|
||||
}
|
||||
|
||||
override fun startPrimaryUse(delta: Float): Boolean {
|
||||
val mousePoint = Point2d(Terrarum.mouseTileX.toDouble(), Terrarum.mouseTileY.toDouble())
|
||||
val actorvalue = ingame.actorNowPlaying.actorValue
|
||||
|
||||
|
||||
using = true
|
||||
|
||||
// linear search filter (check for intersection with tilewise mouse point and tilewise hitbox)
|
||||
// return false if hitting actors
|
||||
ingame.actorContainerActive.forEach {
|
||||
if (it is ActorWBMovable && it.hIntTilewiseHitbox.intersects(mousePoint))
|
||||
return false
|
||||
}
|
||||
|
||||
// return false if there's no tile
|
||||
if (Block.AIR == ingame.world.getTileFromTerrain(Terrarum.mouseTileX, Terrarum.mouseTileY))
|
||||
return false
|
||||
|
||||
|
||||
// filter passed, do the job
|
||||
val swingDmgToFrameDmg = delta.toDouble() / actorvalue.getAsDouble(AVKey.ACTION_INTERVAL)!!
|
||||
|
||||
ingame.world.inflictTerrainDamage(
|
||||
Terrarum.mouseTileX,
|
||||
Terrarum.mouseTileY,
|
||||
Calculate.pickaxePower(ingame.actorNowPlaying, material) * swingDmgToFrameDmg
|
||||
)
|
||||
return true
|
||||
}
|
||||
|
||||
override fun endPrimaryUse(delta: Float): Boolean {
|
||||
using = false
|
||||
// reset action timer to zero
|
||||
ingame.actorNowPlaying.actorValue[AVKey.__ACTION_TIMER] = 0.0
|
||||
return true
|
||||
}
|
||||
}*/
|
||||
|
||||
|
||||
// test water bucket
|
||||
itemCodex[9000] = object : GameItem(9000) {
|
||||
|
||||
override val isUnique: Boolean = true
|
||||
override val originalName: String = "Infinite Water Bucket"
|
||||
|
||||
override var baseMass: Double = 1000.0
|
||||
override var baseToolSize: Double? = null
|
||||
|
||||
override var inventoryCategory: String = "tool"
|
||||
override var stackable: Boolean = false
|
||||
|
||||
override val isDynamic: Boolean = false
|
||||
override val material: Material = Material()
|
||||
|
||||
init {
|
||||
equipPosition = EquipPosition.HAND_GRIP
|
||||
}
|
||||
|
||||
override fun startPrimaryUse(delta: Float): Boolean {
|
||||
val ingame = Terrarum.ingame!! as TerrarumIngame // must be in here
|
||||
ingame.world.setFluid(Terrarum.mouseTileX, Terrarum.mouseTileY, Fluid.WATER, 4f)
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// test lava bucket
|
||||
itemCodex[9001] = object : GameItem(9001) {
|
||||
|
||||
override val isUnique: Boolean = true
|
||||
override val originalName: String = "Infinite Lava Bucket"
|
||||
|
||||
override var baseMass: Double = 1000.0
|
||||
override var baseToolSize: Double? = null
|
||||
|
||||
override var inventoryCategory: String = "tool"
|
||||
override var stackable: Boolean = false
|
||||
|
||||
override val isDynamic: Boolean = false
|
||||
override val material: Material = Material()
|
||||
|
||||
init {
|
||||
equipPosition = EquipPosition.HAND_GRIP
|
||||
}
|
||||
|
||||
override fun startPrimaryUse(delta: Float): Boolean {
|
||||
val ingame = Terrarum.ingame!! as TerrarumIngame // must be in here
|
||||
ingame.world.setFluid(Terrarum.mouseTileX, Terrarum.mouseTileY, Fluid.LAVA, 4f)
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// read from save (if applicable) and fill dynamicItemDescription
|
||||
|
||||
|
||||
|
||||
println()
|
||||
}
|
||||
|
||||
fun registerNewDynamicItem(dynamicID: Int, item: GameItem) {
|
||||
if (AppLoader.IS_DEVELOPMENT_BUILD) {
|
||||
printdbg(this, "Registering new dynamic item $dynamicID (from ${item.originalID})")
|
||||
}
|
||||
@@ -57,17 +251,18 @@ object ItemCodex {
|
||||
operator fun get(code: ItemID?): GameItem? {
|
||||
if (code == null) return null
|
||||
|
||||
if (code.startsWith(PREFIX_DYNAMICITEM))
|
||||
if (code <= ITEM_STATIC.endInclusive) // generic item
|
||||
return itemCodex[code]!!.clone() // from CSV
|
||||
else if (code <= ITEM_DYNAMIC.endInclusive) {
|
||||
return dynamicItemDescription[code]!!
|
||||
else if (code.startsWith(PREFIX_ACTORITEM)) {
|
||||
val a = (Terrarum.ingame!! as TerrarumIngame).getActorByID(code.substring(6).toInt()) // actor item
|
||||
}
|
||||
else {
|
||||
val a = (Terrarum.ingame!! as TerrarumIngame).getActorByID(code) // actor item
|
||||
if (a is CanBeAnItem) return a.itemData
|
||||
|
||||
return null
|
||||
//throw IllegalArgumentException("Attempted to get item data of actor that cannot be an item. ($a)")
|
||||
}
|
||||
else // generic item
|
||||
return itemCodex[code]?.clone() // from CSV
|
||||
}
|
||||
|
||||
fun dynamicToStaticID(dynamicID: ItemID) = dynamicToStaticTable[dynamicID]!!
|
||||
@@ -75,10 +270,6 @@ object ItemCodex {
|
||||
/**
|
||||
* Mainly used by GameItemLoader
|
||||
*/
|
||||
fun set(modname: String, code: Int, item: GameItem) {
|
||||
itemCodex["$modname:$code"] = item
|
||||
}
|
||||
|
||||
operator fun set(code: ItemID, item: GameItem) {
|
||||
itemCodex[code] = item
|
||||
}
|
||||
@@ -89,35 +280,31 @@ object ItemCodex {
|
||||
return getItemImage(item.originalID)
|
||||
}
|
||||
|
||||
fun getItemImage(itemID: ItemID?): TextureRegion? {
|
||||
if (itemID == null) return null
|
||||
|
||||
fun getItemImage(itemOriginalID: Int): TextureRegion {
|
||||
// dynamic item
|
||||
if (itemID.startsWith(PREFIX_DYNAMICITEM)) {
|
||||
return getItemImage(dynamicToStaticID(itemID))
|
||||
}
|
||||
// item
|
||||
else if (itemID.startsWith("item@")) {
|
||||
return itemCodex[itemID]?.itemImage
|
||||
}
|
||||
// TODO: wires
|
||||
// wall
|
||||
else if (itemID.startsWith("wall@")) {
|
||||
val itemSheetNumber = CreateTileAtlas.tileIDtoItemSheetNumber(itemID.substring(5))
|
||||
return BlocksDrawer.tileItemWall.get(
|
||||
itemSheetNumber % ITEM_ATLAS_TILES_X,
|
||||
itemSheetNumber / ITEM_ATLAS_TILES_X
|
||||
)
|
||||
if (itemOriginalID in ITEM_DYNAMIC) {
|
||||
return getItemImage(dynamicToStaticID(itemOriginalID))
|
||||
}
|
||||
// terrain
|
||||
else {
|
||||
val itemSheetNumber = CreateTileAtlas.tileIDtoItemSheetNumber(itemID)
|
||||
else if (itemOriginalID in ITEM_TILES) {
|
||||
return BlocksDrawer.tileItemTerrain.get(
|
||||
itemSheetNumber % ITEM_ATLAS_TILES_X,
|
||||
itemSheetNumber / ITEM_ATLAS_TILES_X
|
||||
itemOriginalID % 16,
|
||||
itemOriginalID / 16
|
||||
)
|
||||
}
|
||||
|
||||
// wall
|
||||
else if (itemOriginalID in ITEM_WALLS) {
|
||||
return BlocksDrawer.tileItemWall.get(
|
||||
(itemOriginalID.minus(ITEM_WALLS.first) % 16),
|
||||
(itemOriginalID.minus(ITEM_WALLS.first) / 16)
|
||||
)
|
||||
}
|
||||
// wire
|
||||
/*else if (itemOriginalID in ITEM_WIRES) {
|
||||
return BlocksDrawer.tilesWire.get((itemOriginalID % 16) * 16, itemOriginalID / 16)
|
||||
}*/
|
||||
else
|
||||
return itemCodex[itemOriginalID]?.itemImage ?: itemImagePlaceholder
|
||||
}
|
||||
|
||||
fun hasItem(itemID: Int): Boolean = dynamicItemDescription.containsKey(itemID)
|
||||
|
||||
@@ -16,8 +16,6 @@ import net.torvald.terrarum.modulebasegame.gameactors.ActorHumanoid
|
||||
import net.torvald.terrarum.modulebasegame.gameworld.GameWorldExtension
|
||||
import net.torvald.terrarum.modulebasegame.gameworld.WorldTime
|
||||
import net.torvald.terrarum.modulebasegame.ui.Notification
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIBuildingMakerBlockChooser
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIBuildingMakerPenMenu
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIPaletteSelector
|
||||
import net.torvald.terrarum.modulebasegame.weather.WeatherMixer
|
||||
import net.torvald.terrarum.realestate.LandUtil
|
||||
@@ -29,6 +27,7 @@ import net.torvald.terrarum.serialise.toLittleShort
|
||||
import net.torvald.terrarum.serialise.toULittle48
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
import net.torvald.terrarum.ui.UINSMenu
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas.TILE_SIZE
|
||||
import net.torvald.terrarum.worlddrawer.WorldCamera
|
||||
import java.io.File
|
||||
import java.io.FileOutputStream
|
||||
@@ -84,19 +83,19 @@ class BuildingMaker(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
println("[BuildingMaker] Generating builder world...")
|
||||
|
||||
for (y in 0 until gameWorld.height) {
|
||||
gameWorld.setTileWall(0, y, Block.ILLUMINATOR_RED, true)
|
||||
gameWorld.setTileWall(gameWorld.width - 1, y, Block.ILLUMINATOR_RED, true)
|
||||
gameWorld.setTileTerrain(0, y, Block.ILLUMINATOR_RED_OFF, true)
|
||||
gameWorld.setTileTerrain(gameWorld.width - 1, y, Block.ILLUMINATOR_RED_OFF, true)
|
||||
gameWorld.setTileWall(0, y, Block.ILLUMINATOR_RED)
|
||||
gameWorld.setTileWall(gameWorld.width - 1, y, Block.ILLUMINATOR_RED)
|
||||
gameWorld.setTileTerrain(0, y, Block.ILLUMINATOR_RED_OFF)
|
||||
gameWorld.setTileTerrain(gameWorld.width - 1, y, Block.ILLUMINATOR_RED_OFF)
|
||||
}
|
||||
|
||||
for (y in 150 until gameWorld.height) {
|
||||
for (x in 1 until gameWorld.width - 1) {
|
||||
// wall layer
|
||||
gameWorld.setTileWall(x, y, Block.DIRT, true)
|
||||
gameWorld.setTileWall(x, y, Block.DIRT)
|
||||
|
||||
// terrain layer
|
||||
gameWorld.setTileTerrain(x, y, if (y == 150) Block.GRASS else Block.DIRT, true)
|
||||
gameWorld.setTileTerrain(x, y, if (y == 150) Block.GRASS else Block.DIRT)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -368,13 +367,13 @@ class BuildingMaker(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
|
||||
// make pen work HERE
|
||||
// when LEFT mouse is down
|
||||
if (!tappedOnUI && Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary")) && !mouseOnUI) {
|
||||
if (!tappedOnUI && Gdx.input.isButtonPressed(AppLoader.getConfigInt("mouseprimary")) && !mouseOnUI) {
|
||||
|
||||
makePenWork(Terrarum.mouseTileX, Terrarum.mouseTileY)
|
||||
// TODO drag support using bresenham's algo
|
||||
// for some reason it just doesn't work...
|
||||
}
|
||||
else if (!uiPenMenu.isVisible && Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mousesecondary"))) {
|
||||
else if (!uiPenMenu.isVisible && Gdx.input.isButtonPressed(AppLoader.getConfigInt("mousesecondary"))) {
|
||||
// open pen menu
|
||||
// position the menu to where the cursor is
|
||||
uiPenMenu.posX = Terrarum.mouseScreenX - uiPenMenu.width / 2
|
||||
@@ -424,22 +423,22 @@ class BuildingMaker(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
when (currentPenMode) {
|
||||
// test paint terrain layer
|
||||
PENMODE_PENCIL -> {
|
||||
if (palSelection.startsWith("wall@"))
|
||||
world.setTileWall(x, y, palSelection.substring(5), true)
|
||||
else
|
||||
world.setTileTerrain(x, y, palSelection, true)
|
||||
if (palSelection < BlockCodex.MAX_TERRAIN_TILES)
|
||||
world.setTileTerrain(x, y, palSelection)
|
||||
else if (palSelection < 2 * BlockCodex.MAX_TERRAIN_TILES)
|
||||
world.setTileWall(x, y, palSelection - BlockCodex.MAX_TERRAIN_TILES)
|
||||
}
|
||||
PENMODE_PENCIL_ERASE -> {
|
||||
if (currentPenTarget and PENTARGET_WALL != 0)
|
||||
world.setTileWall(x, y, Block.AIR, true)
|
||||
world.setTileWall(x, y, Block.AIR)
|
||||
else
|
||||
world.setTileTerrain(x, y, Block.AIR, true)
|
||||
world.setTileTerrain(x, y, Block.AIR)
|
||||
}
|
||||
PENMODE_EYEDROPPER -> {
|
||||
uiPaletteSelector.fore = if (world.getTileFromTerrain(x, y) == Block.AIR)
|
||||
"wall@"+world.getTileFromWall(x, y)
|
||||
world.getTileFromWall(x, y)!! + BlockCodex.MAX_TERRAIN_TILES
|
||||
else
|
||||
world.getTileFromTerrain(x, y)
|
||||
world.getTileFromTerrain(x, y)!!
|
||||
}
|
||||
PENMODE_MARQUEE -> {
|
||||
addBlockMarker(x, y)
|
||||
@@ -455,7 +454,7 @@ class BuildingMaker(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
return selection.last() - selection.first()
|
||||
}
|
||||
|
||||
/*private fun serialiseSelection(outfile: File) {
|
||||
private fun serialiseSelection(outfile: File) {
|
||||
// save format: sparse list encoded in following binary format:
|
||||
/*
|
||||
Header: TEaT0bLD -- magic: Terrarum Attachment
|
||||
@@ -498,7 +497,7 @@ class BuildingMaker(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
}
|
||||
fos.write(FILE_FOOTER)
|
||||
fos.close()
|
||||
}*/
|
||||
}
|
||||
}
|
||||
|
||||
class BuildingMakerController(val screen: BuildingMaker) : InputAdapter() {
|
||||
|
||||
@@ -6,7 +6,6 @@ import net.torvald.terrarum.CommonResourcePool
|
||||
import net.torvald.terrarum.ModMgr
|
||||
import net.torvald.terrarum.ModuleEntryPoint
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.blockproperties.BlockProp
|
||||
import net.torvald.terrarum.gameitem.GameItem
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.itemproperties.MaterialCodex
|
||||
@@ -53,14 +52,35 @@ class EntryPoint : ModuleEntryPoint() {
|
||||
|
||||
// blocks.csvs are loaded by ModMgr beforehand
|
||||
// block items (blocks and walls are the same thing basically)
|
||||
for (tile in BlockCodex.getAll()) {
|
||||
ItemCodex[tile.id] = makeNewItemObj(tile, false)
|
||||
for (i in ItemCodex.ITEM_TILES + ItemCodex.ITEM_WALLS) {
|
||||
val blockProp = BlockCodex.getOrNull(i % ItemCodex.ITEM_WALLS.first)
|
||||
|
||||
if (IS_DEVELOPMENT_BUILD) print(tile.id+" ")
|
||||
if (blockProp != null) {
|
||||
ItemCodex.itemCodex[i] = object : GameItem(i) {
|
||||
override val isUnique: Boolean = false
|
||||
override var baseMass: Double = blockProp.density / 1000.0
|
||||
override var baseToolSize: Double? = null
|
||||
override val originalName = blockProp.nameKey
|
||||
override var stackable = true
|
||||
override var inventoryCategory = if (i in ItemCodex.ITEM_TILES) Category.BLOCK else Category.WALL
|
||||
override var isDynamic = false
|
||||
override val material = MaterialCodex.getOrDefault(blockProp.material)
|
||||
|
||||
if (BlockCodex[tile.id].isWallable) {
|
||||
ItemCodex["wall@" + tile.id] = makeNewItemObj(tile, true)
|
||||
if (IS_DEVELOPMENT_BUILD) print("wall@" + tile.id + " ")
|
||||
init {
|
||||
equipPosition = EquipPosition.HAND_GRIP
|
||||
|
||||
if (IS_DEVELOPMENT_BUILD)
|
||||
print("$originalID ")
|
||||
}
|
||||
|
||||
override fun startPrimaryUse(delta: Float): Boolean {
|
||||
return BlockBase.blockStartPrimaryUse(this, i, delta)
|
||||
}
|
||||
|
||||
override fun effectWhenEquipped(delta: Float) {
|
||||
BlockBase.blockEffectWhenEquipped(delta)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -69,32 +89,6 @@ class EntryPoint : ModuleEntryPoint() {
|
||||
println("[Basegame.EntryPoint] Welcome back!")
|
||||
}
|
||||
|
||||
private fun makeNewItemObj(tile: BlockProp, isWall: Boolean) = object : GameItem(
|
||||
if (isWall) "wall@"+tile.id else tile.id
|
||||
) {
|
||||
override val isUnique: Boolean = false
|
||||
override var baseMass: Double = tile.density / 1000.0
|
||||
override var baseToolSize: Double? = null
|
||||
override val originalName = tile.nameKey
|
||||
override var stackable = true
|
||||
override var inventoryCategory = if (isWall) Category.WALL else Category.BLOCK
|
||||
override var isDynamic = false
|
||||
override val material = MaterialCodex.getOrDefault(tile.material)
|
||||
|
||||
init {
|
||||
equipPosition = EquipPosition.HAND_GRIP
|
||||
}
|
||||
|
||||
override fun startPrimaryUse(delta: Float): Boolean {
|
||||
return BlockBase.blockStartPrimaryUse(this, dynamicID, delta)
|
||||
}
|
||||
|
||||
override fun effectWhenEquipped(delta: Float) {
|
||||
BlockBase.blockEffectWhenEquipped(delta)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
override fun dispose() {
|
||||
WatchFont.dispose()
|
||||
}
|
||||
|
||||
@@ -51,10 +51,10 @@ object IngameRenderer : Disposable {
|
||||
val shaderAtoGrey: ShaderProgram
|
||||
val shaderPassthru = SpriteBatch.createDefaultShader()
|
||||
|
||||
private val WIDTH = AppLoader.screenW
|
||||
private val HEIGHT = AppLoader.screenH
|
||||
private val WIDTHF = WIDTH.toFloat()
|
||||
private val HEIGHTF = HEIGHT.toFloat()
|
||||
private val width = AppLoader.screenW
|
||||
private val height = AppLoader.screenH
|
||||
private val widthf = width.toFloat()
|
||||
private val heightf = height.toFloat()
|
||||
|
||||
private var initDone = false
|
||||
|
||||
@@ -586,13 +586,13 @@ object IngameRenderer : Disposable {
|
||||
private fun invokeInit() {
|
||||
if (!initDone) {
|
||||
batch = SpriteBatch()
|
||||
camera = OrthographicCamera(WIDTHF, HEIGHTF)
|
||||
camera = OrthographicCamera(widthf, heightf)
|
||||
|
||||
camera.setToOrtho(true, WIDTHF, HEIGHTF)
|
||||
camera.setToOrtho(true, widthf, heightf)
|
||||
camera.update()
|
||||
Gdx.gl20.glViewport(0, 0, WIDTH, HEIGHT)
|
||||
Gdx.gl20.glViewport(0, 0, width, height)
|
||||
|
||||
resize(WIDTH, HEIGHT)
|
||||
resize(width, height)
|
||||
|
||||
initDone = true
|
||||
}
|
||||
|
||||
@@ -5,13 +5,12 @@ import com.badlogic.gdx.Input
|
||||
import com.badlogic.gdx.graphics.Camera
|
||||
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||
import net.torvald.EMDASH
|
||||
import net.torvald.UnsafeHelper
|
||||
import net.torvald.terrarum.*
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.blockproperties.BlockPropUtil
|
||||
import net.torvald.terrarum.blockstats.BlockStats
|
||||
import net.torvald.terrarum.blockstats.MinimapComposer
|
||||
import net.torvald.terrarum.concurrent.ThreadExecutor
|
||||
import net.torvald.terrarum.concurrent.ThreadParallel
|
||||
import net.torvald.terrarum.console.Authenticator
|
||||
import net.torvald.terrarum.gameactors.Actor
|
||||
import net.torvald.terrarum.gameactors.ActorWithBody
|
||||
@@ -38,7 +37,6 @@ import net.torvald.terrarum.worlddrawer.WorldCamera
|
||||
import net.torvald.util.CircularArray
|
||||
import java.util.*
|
||||
import java.util.concurrent.locks.ReentrantLock
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
|
||||
/**
|
||||
@@ -92,7 +90,7 @@ open class TerrarumIngame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
" $EMDASH F: ${Gdx.graphics.framesPerSecond}" +
|
||||
if (AppLoader.IS_DEVELOPMENT_BUILD)
|
||||
" (ΔF${Terrarum.updateRateStr})" +
|
||||
" $EMDASH M: J${Terrarum.memJavaHeap}M / N${Terrarum.memNativeHeap}M / U${Terrarum.memUnsafe}M / X${Terrarum.memXmx}M"
|
||||
" $EMDASH M: J${Terrarum.memJavaHeap}M / N${Terrarum.memNativeHeap}M / X${Terrarum.memXmx}M"
|
||||
else
|
||||
""
|
||||
}
|
||||
@@ -315,8 +313,8 @@ open class TerrarumIngame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
|
||||
// >- queue up game UIs that should pause the world -<
|
||||
uiInventoryPlayer = UIInventoryFull(actorNowPlaying!!,
|
||||
toggleKeyLiteral = AppLoader.getConfigInt("config_keyinventory"),
|
||||
toggleButtonLiteral = AppLoader.getConfigInt("config_gamepadstart")
|
||||
toggleKeyLiteral = AppLoader.getConfigInt("keyinventory"),
|
||||
toggleButtonLiteral = AppLoader.getConfigInt("gamepadstart")
|
||||
)
|
||||
uiInventoryPlayer.setPosition(0, 0)
|
||||
|
||||
@@ -399,8 +397,6 @@ open class TerrarumIngame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
}// END enter
|
||||
|
||||
override fun worldPrimaryClickStart(delta: Float) {
|
||||
//println("[Ingame] worldPrimaryClickStart $delta")
|
||||
|
||||
// bring up the UIs of the fixtures (e.g. crafting menu from a crafting table)
|
||||
var uiOpened = false
|
||||
|
||||
@@ -411,7 +407,7 @@ open class TerrarumIngame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
}
|
||||
// scan for the one with non-null UI.
|
||||
// what if there's multiple of such fixtures? whatever, you are supposed to DISALLOW such situation.
|
||||
for (kk in actorsUnderMouse.indices) {
|
||||
for (kk in 0 until actorsUnderMouse.size) {
|
||||
actorsUnderMouse[kk].mainUI?.let {
|
||||
uiOpened = true
|
||||
|
||||
@@ -662,15 +658,15 @@ open class TerrarumIngame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
}
|
||||
|
||||
/** Send message to notifier UI and toggle the UI as opened. */
|
||||
override fun sendNotification(messages: Array<String>) {
|
||||
fun sendNotification(messages: Array<String>) {
|
||||
(notifier as Notification).sendNotification(messages.toList())
|
||||
}
|
||||
|
||||
override fun sendNotification(messages: List<String>) {
|
||||
fun sendNotification(messages: List<String>) {
|
||||
(notifier as Notification).sendNotification(messages)
|
||||
}
|
||||
|
||||
override fun sendNotification(singleMessage: String) = sendNotification(listOf(singleMessage))
|
||||
fun sendNotification(singleMessage: String) = sendNotification(listOf(singleMessage))
|
||||
|
||||
fun wakeDormantActors() {
|
||||
var actorContainerSize = actorContainerInactive.size
|
||||
@@ -723,20 +719,19 @@ open class TerrarumIngame(batch: SpriteBatch) : IngameInstance(batch) {
|
||||
*/
|
||||
fun updateActors(delta: Float) {
|
||||
if (false) { // don't multithread this for now, it's SLOWER //if (Terrarum.MULTITHREAD && actorContainerActive.size > Terrarum.THREADS) {
|
||||
ThreadExecutor.renew()
|
||||
|
||||
val actors = actorContainerActive.size.toFloat()
|
||||
// set up indices
|
||||
for (i in 0..AppLoader.THREAD_COUNT - 1) {
|
||||
ThreadExecutor.submit(
|
||||
for (i in 0..AppLoader.THREADS - 1) {
|
||||
ThreadParallel.map(
|
||||
i, "ActorUpdate",
|
||||
ThreadActorUpdate(
|
||||
actors.div(AppLoader.THREAD_COUNT).times(i).roundToInt(),
|
||||
actors.div(AppLoader.THREAD_COUNT).times(i + 1).roundToInt() - 1
|
||||
actors.div(AppLoader.THREADS).times(i).roundInt(),
|
||||
actors.div(AppLoader.THREADS).times(i + 1).roundInt() - 1
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
ThreadExecutor.join()
|
||||
ThreadParallel.startAll()
|
||||
|
||||
actorNowPlaying?.update(delta)
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
package net.torvald.terrarum.modulebasegame.ui
|
||||
package net.torvald.terrarum.modulebasegame
|
||||
|
||||
import com.badlogic.gdx.Gdx
|
||||
import com.badlogic.gdx.graphics.Camera
|
||||
@@ -6,16 +6,13 @@ import com.badlogic.gdx.graphics.Color
|
||||
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.blendNormal
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.fillRect
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulebasegame.BuildingMaker
|
||||
import net.torvald.terrarum.modulebasegame.ui.ItemSlotImageFactory.CELLCOLOUR_WHITE
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
import net.torvald.terrarum.ui.UIItemImageButton
|
||||
import net.torvald.terrarum.ui.UIItemTextButtonList
|
||||
import net.torvald.terrarum.ui.UIItemTextButtonList.Companion.DEFAULT_BACKGROUNDCOL
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
/**
|
||||
@@ -31,18 +28,27 @@ class UIBuildingMakerBlockChooser(val parent: BuildingMaker): UICanvas() {
|
||||
const val MENUBAR_SIZE = 72
|
||||
const val SCROLLBAR_SIZE = 24
|
||||
|
||||
const val WIDTH = TILES_X * TILESREGION_SIZE + SCROLLBAR_SIZE + MENUBAR_SIZE
|
||||
const val HEIGHT = TILES_Y * TILESREGION_SIZE
|
||||
const val WIDTH = TILES_X*TILESREGION_SIZE + SCROLLBAR_SIZE + MENUBAR_SIZE
|
||||
const val HEIGHT = TILES_Y*TILESREGION_SIZE
|
||||
}
|
||||
|
||||
override var width = WIDTH
|
||||
override var height = HEIGHT
|
||||
override var openCloseTime = 0f
|
||||
|
||||
val palette = ArrayList<UIItemImageButton>()
|
||||
|
||||
// TODO scrolling of the palette, as the old method flat out won't work with The Flattening
|
||||
|
||||
private val palette = Array<UIItemImageButton>(TILES_X * TILES_Y) {
|
||||
// initialise with terrain blocks
|
||||
UIItemImageButton(
|
||||
this, ItemCodex.getItemImage(it),
|
||||
initialX = MENUBAR_SIZE + (it % 16) * TILESREGION_SIZE,
|
||||
initialY = (it / 16) * TILESREGION_SIZE,
|
||||
highlightable = false,
|
||||
width = TILESREGION_SIZE,
|
||||
height = TILESREGION_SIZE,
|
||||
highlightCol = Color.WHITE,
|
||||
activeCol = Color.WHITE
|
||||
)
|
||||
}
|
||||
private val tabs = UIItemTextButtonList(
|
||||
this, arrayOf("Terrain", "Wall", "Wire"),
|
||||
0, 0, textAreaWidth = MENUBAR_SIZE, width = MENUBAR_SIZE,
|
||||
@@ -55,25 +61,12 @@ class UIBuildingMakerBlockChooser(val parent: BuildingMaker): UICanvas() {
|
||||
)
|
||||
|
||||
init {
|
||||
palette.forEachIndexed { index, it ->
|
||||
uiItems.add(it)
|
||||
|
||||
BlockCodex.getAll().forEachIndexed { index, prop ->
|
||||
val paletteItem = UIItemImageButton(
|
||||
this, ItemCodex.getItemImage(prop.id)!!,
|
||||
initialX = MENUBAR_SIZE + (index % 16) * TILESREGION_SIZE,
|
||||
initialY = (index / 16) * TILESREGION_SIZE,
|
||||
highlightable = false,
|
||||
width = TILESREGION_SIZE,
|
||||
height = TILESREGION_SIZE,
|
||||
highlightCol = Color.WHITE,
|
||||
activeCol = Color.WHITE
|
||||
)
|
||||
|
||||
paletteItem.clickOnceListener = { _, _, _ ->
|
||||
parent.setPencilColour(prop.id)
|
||||
it.clickOnceListener = { _, _, _ ->
|
||||
parent.setPencilColour(paletteScroll * 16 + index)
|
||||
}
|
||||
|
||||
uiItems.add(paletteItem)
|
||||
palette.add(paletteItem)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -88,7 +81,7 @@ class UIBuildingMakerBlockChooser(val parent: BuildingMaker): UICanvas() {
|
||||
}
|
||||
|
||||
// respond to click
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary"))) {
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("mouseprimary"))) {
|
||||
// scroll bar
|
||||
if (relativeMouseX in width - SCROLLBAR_SIZE until width && relativeMouseY in 0 until height) {
|
||||
mouseOnScroll = true
|
||||
@@ -125,7 +118,9 @@ class UIBuildingMakerBlockChooser(val parent: BuildingMaker): UICanvas() {
|
||||
}
|
||||
|
||||
private fun rebuildPalette() {
|
||||
|
||||
palette.forEachIndexed { index, it ->
|
||||
it.image = ItemCodex.getItemImage(paletteScroll * 16 + index)
|
||||
}
|
||||
}
|
||||
|
||||
override fun renderUI(batch: SpriteBatch, camera: Camera) {
|
||||
@@ -1,4 +1,4 @@
|
||||
package net.torvald.terrarum.modulebasegame.ui
|
||||
package net.torvald.terrarum.modulebasegame
|
||||
|
||||
import com.badlogic.gdx.Gdx
|
||||
import com.badlogic.gdx.Input
|
||||
@@ -7,12 +7,11 @@ import com.badlogic.gdx.graphics.Color
|
||||
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||
import net.torvald.terrarum.*
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulebasegame.BuildingMaker
|
||||
import net.torvald.terrarum.modulebasegame.ui.ItemSlotImageFactory
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
import net.torvald.terrarum.ui.UIItemImageButton
|
||||
import net.torvald.terrarumsansbitmap.gdx.TextureRegionPack
|
||||
import org.dyn4j.geometry.Vector2
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2019-02-16.
|
||||
@@ -58,8 +57,8 @@ class UIBuildingMakerPenMenu(val parent: BuildingMaker): UICanvas() {
|
||||
backgroundCol = Color(0),
|
||||
highlightBackCol = Color(0),
|
||||
activeBackCol = Color(0),
|
||||
initialX = newvec.x.roundToInt(),
|
||||
initialY = newvec.y.roundToInt(),
|
||||
initialX = newvec.x.roundInt(),
|
||||
initialY = newvec.y.roundInt(),
|
||||
width = ICON_SIZE, height = ICON_SIZE,
|
||||
highlightable = false
|
||||
)
|
||||
@@ -99,7 +98,7 @@ class UIBuildingMakerPenMenu(val parent: BuildingMaker): UICanvas() {
|
||||
uiItems.add(button)
|
||||
|
||||
button.clickOnceListener = { _, _, b ->
|
||||
if (b == AppLoader.getConfigInt("config_mouseprimary")) {
|
||||
if (b == AppLoader.getConfigInt("mouseprimary")) {
|
||||
toolButtonsJob[index].invoke()
|
||||
closeGracefully()
|
||||
}
|
||||
@@ -133,7 +132,7 @@ class UIBuildingMakerPenMenu(val parent: BuildingMaker): UICanvas() {
|
||||
}
|
||||
|
||||
// primary click
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary"))) {
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("mouseprimary"))) {
|
||||
// close by clicking close button or out-of-boud
|
||||
if (mouseVec.distanceSquared(RADIUS, RADIUS) !in CLOSE_BUTTON_RADIUS.sqr()..RADIUSF.sqr()) {
|
||||
closeGracefully()
|
||||
@@ -153,17 +152,17 @@ class UIBuildingMakerPenMenu(val parent: BuildingMaker): UICanvas() {
|
||||
|
||||
// draw blocks slot
|
||||
batch.color = blockCellCol
|
||||
val slotConfig = AppLoader.getConfigStringArray("buildingmakerfavs")
|
||||
val slotConfig = AppLoader.getConfigIntArray("buildingmakerfavs")
|
||||
for (i in 0 until PALETTE_SIZE) {
|
||||
val x = blockCellPos[i].x.roundToInt().toFloat()
|
||||
val y = blockCellPos[i].y.roundToInt().toFloat()
|
||||
val x = blockCellPos[i].x.roundInt().toFloat()
|
||||
val y = blockCellPos[i].y.roundInt().toFloat()
|
||||
batch.color = blockCellCol
|
||||
repeat((i == mouseOnBlocksSlot).toInt() + 1) { batch.fillCircle(x - BLOCK_BACK_RADIUS, y - BLOCK_BACK_RADIUS, BLOCK_BACK_SIZE.toFloat(), BLOCK_BACK_SIZE.toFloat()) }
|
||||
batch.color = Color.WHITE
|
||||
batch.draw(ItemCodex.getItemImage(slotConfig[i]), x - 16, y - 16, 32f, 32f)
|
||||
|
||||
// update as well while looping
|
||||
if (i == mouseOnBlocksSlot && Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary"))) {
|
||||
if (i == mouseOnBlocksSlot && Gdx.input.isButtonPressed(AppLoader.getConfigInt("mouseprimary"))) {
|
||||
parent.setPencilColour(slotConfig[i])
|
||||
closeGracefully()
|
||||
}
|
||||
@@ -1,14 +1,11 @@
|
||||
package net.torvald.terrarum.modulebasegame
|
||||
|
||||
import com.badlogic.gdx.Gdx
|
||||
import com.badlogic.gdx.ScreenAdapter
|
||||
import com.badlogic.gdx.graphics.Color
|
||||
import com.badlogic.gdx.graphics.Pixmap
|
||||
import com.badlogic.gdx.graphics.Texture
|
||||
import net.torvald.terrarum.*
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.blockproperties.BlockProp
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.util.CircularArray
|
||||
import kotlin.math.roundToInt
|
||||
@@ -32,7 +29,7 @@ class WorldgenLoadScreen(screenToBeLoaded: IngameInstance, private val worldwidt
|
||||
|
||||
companion object {
|
||||
private const val WIDTH_RATIO = 0.7
|
||||
private const val PREVIEW_UPDATE_RATE = AppLoader.UPDATE_RATE
|
||||
private const val PREVIEW_UPDATE_RATE = 1 / 5f
|
||||
|
||||
private val COL_TERR = Color.WHITE
|
||||
private val COL_WALLED = Color(.5f, .5f, .5f, 1f)
|
||||
@@ -60,6 +57,8 @@ class WorldgenLoadScreen(screenToBeLoaded: IngameInstance, private val worldwidt
|
||||
}
|
||||
|
||||
override fun render(delta: Float) {
|
||||
//println("WorldgenLoadScreenRender")
|
||||
|
||||
gdxClearAndSetBlend(.094f, .094f, .094f, 0f)
|
||||
|
||||
previewRenderCounter += delta
|
||||
@@ -95,9 +94,7 @@ class WorldgenLoadScreen(screenToBeLoaded: IngameInstance, private val worldwidt
|
||||
val wx = (world.width.toFloat() / previewWidth * x).roundToInt()
|
||||
val wy = (world.height.toFloat() / previewHeight * y).roundToInt()
|
||||
|
||||
val outCol = if (BlockCodex[world.getTileFromTerrain(wx, wy)].isSolid) COL_TERR
|
||||
else if (BlockCodex[world.getTileFromWall(wx, wy)].isSolid) COL_WALLED
|
||||
else COL_AIR
|
||||
val outCol = if (world.getTileFromTerrain(wx, wy) > 15) COL_TERR else if (world.getTileFromWall(wx, wy) > 15) COL_WALLED else COL_AIR
|
||||
|
||||
previewPixmap.setColor(outCol)
|
||||
previewPixmap.drawPixel(x, previewHeight - 1 - y) // this flips Y
|
||||
@@ -106,6 +103,9 @@ class WorldgenLoadScreen(screenToBeLoaded: IngameInstance, private val worldwidt
|
||||
|
||||
}
|
||||
|
||||
override fun addMessage(msg: String) {
|
||||
super.addMessage(msg)
|
||||
}
|
||||
|
||||
override fun dispose() {
|
||||
if (!previewPixmap.isDisposed)
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
package net.torvald.terrarum.modulebasegame.console
|
||||
|
||||
import net.torvald.gdx.graphics.Cvec
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.console.ConsoleCommand
|
||||
@@ -8,7 +7,6 @@ import net.torvald.terrarum.console.Echo
|
||||
import net.torvald.terrarum.console.EchoError
|
||||
import net.torvald.terrarum.utils.RasterWriter
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||
import net.torvald.terrarum.worlddrawer.toRGBA
|
||||
import java.io.File
|
||||
import java.io.IOException
|
||||
|
||||
@@ -33,8 +31,7 @@ internal object ExportMap : ConsoleCommand {
|
||||
var mapDataPointer = 0
|
||||
|
||||
for (tile in world.terrainIterator()) {
|
||||
val tileNumber = CreateTileAtlas.tileIDtoItemSheetNumber(tile)
|
||||
val colArray = CreateTileAtlas.terrainTileColourMap.get(tileNumber)!!.toByteArray()
|
||||
val colArray = CreateTileAtlas.terrainTileColourMap.getRaw(tile % 16, tile / 16).toByteArray()
|
||||
|
||||
for (i in 0..2) {
|
||||
mapData[mapDataPointer + i] = colArray[i]
|
||||
@@ -74,13 +71,11 @@ internal object ExportMap : ConsoleCommand {
|
||||
/***
|
||||
* R-G-B-A order for RGBA input value
|
||||
*/
|
||||
private fun Cvec.toByteArray() = this.toRGBA().toByteArray()
|
||||
|
||||
private fun Int.toByteArray() = byteArrayOf(
|
||||
this.ushr(24).and(255).toByte(),
|
||||
this.ushr(16).and(255).toByte(),
|
||||
this.ushr(8).and(255).toByte(),
|
||||
this.and(255).toByte()
|
||||
this.shr(24).and(0xff).toByte(),
|
||||
this.shr(16).and(0xff).toByte(),
|
||||
this.shr(8).and(0xff).toByte(),
|
||||
this.and(0xff).toByte()
|
||||
)
|
||||
|
||||
override fun printUsage() {
|
||||
|
||||
@@ -4,7 +4,6 @@ import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.console.ConsoleCommand
|
||||
import net.torvald.terrarum.console.Echo
|
||||
import net.torvald.terrarum.console.EchoError
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.Pocketed
|
||||
@@ -23,10 +22,10 @@ internal object Inventory : ConsoleCommand {
|
||||
else {
|
||||
when (args[1]) {
|
||||
"list" -> listInventory()
|
||||
"add" -> if (args.size > 3) addItem(args[2], args[3].toInt())
|
||||
else addItem(args[2])
|
||||
"add" -> if (args.size > 3) addItem(args[2].toInt(), args[3].toInt())
|
||||
else addItem(args[2].toInt())
|
||||
"target" -> setTarget(args[2].toInt())
|
||||
"equip" -> equipItem(args[2])
|
||||
"equip" -> equipItem(args[2].toInt())
|
||||
else -> printUsage()
|
||||
}
|
||||
}
|
||||
@@ -58,13 +57,13 @@ internal object Inventory : ConsoleCommand {
|
||||
}
|
||||
}
|
||||
|
||||
private fun addItem(refId: ItemID, amount: Int = 1) {
|
||||
private fun addItem(refId: Int, amount: Int = 1) {
|
||||
if (target != null) {
|
||||
target!!.addItem(ItemCodex[refId]!!, amount)
|
||||
}
|
||||
}
|
||||
|
||||
private fun equipItem(refId: ItemID) {
|
||||
private fun equipItem(refId: Int) {
|
||||
if (target != null) {
|
||||
val item = ItemCodex[refId]!!
|
||||
target!!.equipItem(item)
|
||||
|
||||
@@ -68,16 +68,16 @@ open class ActorHumanoid(
|
||||
|
||||
override var color: Cvec
|
||||
get() = Cvec(
|
||||
(actorValue.getAsFloat(AVKey.LUMR) ?: 0f),
|
||||
(actorValue.getAsFloat(AVKey.LUMG) ?: 0f),
|
||||
(actorValue.getAsFloat(AVKey.LUMB) ?: 0f),
|
||||
(actorValue.getAsFloat(AVKey.LUMA) ?: 0f)
|
||||
(actorValue.getAsFloat(AVKey.LUMR) ?: 0f) / LightmapRenderer.MUL_FLOAT,
|
||||
(actorValue.getAsFloat(AVKey.LUMG) ?: 0f) / LightmapRenderer.MUL_FLOAT,
|
||||
(actorValue.getAsFloat(AVKey.LUMB) ?: 0f) / LightmapRenderer.MUL_FLOAT,
|
||||
(actorValue.getAsFloat(AVKey.LUMA) ?: 0f) / LightmapRenderer.MUL_FLOAT
|
||||
)
|
||||
set(value) {
|
||||
actorValue[AVKey.LUMR] = value.r
|
||||
actorValue[AVKey.LUMG] = value.g
|
||||
actorValue[AVKey.LUMB] = value.b
|
||||
actorValue[AVKey.LUMA] = value.a
|
||||
actorValue[AVKey.LUMR] = value.r * LightmapRenderer.MUL_FLOAT
|
||||
actorValue[AVKey.LUMG] = value.g * LightmapRenderer.MUL_FLOAT
|
||||
actorValue[AVKey.LUMB] = value.b * LightmapRenderer.MUL_FLOAT
|
||||
actorValue[AVKey.LUMA] = value.a * LightmapRenderer.MUL_FLOAT
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -168,7 +168,7 @@ open class ActorHumanoid(
|
||||
|
||||
private var jumpJustPressedLatched = false
|
||||
|
||||
@Transient private val nullItem = object : GameItem("item@basegame:0") {
|
||||
@Transient private val nullItem = object : GameItem(0) {
|
||||
override val isUnique: Boolean = false
|
||||
override var baseMass: Double = 0.0
|
||||
override var baseToolSize: Double? = null
|
||||
@@ -231,22 +231,22 @@ open class ActorHumanoid(
|
||||
|
||||
private fun updateGamerControlBox() {
|
||||
if (isGamer) {
|
||||
isUpDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyup"))
|
||||
isLeftDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyleft"))
|
||||
isDownDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keydown"))
|
||||
isRightDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyright"))
|
||||
isJumpDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyjump"))
|
||||
isUpDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyup"))
|
||||
isLeftDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyleft"))
|
||||
isDownDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("keydown"))
|
||||
isRightDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyright"))
|
||||
isJumpDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyjump"))
|
||||
|
||||
val gamepad = AppLoader.gamepad
|
||||
|
||||
if (gamepad != null) {
|
||||
axisX = gamepad.getAxis(AppLoader.getConfigInt("config_gamepadaxislx"))
|
||||
axisY = gamepad.getAxis(AppLoader.getConfigInt("config_gamepadaxisly"))
|
||||
axisRX = gamepad.getAxis(AppLoader.getConfigInt("config_gamepadaxisrx"))
|
||||
axisRY = gamepad.getAxis(AppLoader.getConfigInt("config_gamepadaxisry"))
|
||||
axisX = gamepad.getAxis(AppLoader.getConfigInt("gamepadaxislx"))
|
||||
axisY = gamepad.getAxis(AppLoader.getConfigInt("gamepadaxisly"))
|
||||
axisRX = gamepad.getAxis(AppLoader.getConfigInt("gamepadaxisrx"))
|
||||
axisRY = gamepad.getAxis(AppLoader.getConfigInt("gamepadaxisry"))
|
||||
|
||||
isJumpDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyjump")) ||
|
||||
gamepad.getButton(AppLoader.getConfigInt("config_gamepadltrigger"))
|
||||
isJumpDown = Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyjump")) ||
|
||||
gamepad.getButton(AppLoader.getConfigInt("gamepadltrigger"))
|
||||
}
|
||||
|
||||
if (isJumpJustDown && jumpJustPressedLatched) {
|
||||
@@ -315,11 +315,11 @@ open class ActorHumanoid(
|
||||
// ↑F, ↓S
|
||||
if (isRightDown && !isLeftDown) {
|
||||
walkHorizontal(false, AXIS_KEYBOARD)
|
||||
prevHMoveKey = AppLoader.getConfigInt("config_keyright")
|
||||
prevHMoveKey = AppLoader.getConfigInt("keyright")
|
||||
} // ↓F, ↑S
|
||||
else if (isLeftDown && !isRightDown) {
|
||||
walkHorizontal(true, AXIS_KEYBOARD)
|
||||
prevHMoveKey = AppLoader.getConfigInt("config_keyleft")
|
||||
prevHMoveKey = AppLoader.getConfigInt("keyleft")
|
||||
} // ↓F, ↓S
|
||||
/*else if (isLeftDown && isRightDown) {
|
||||
if (prevHMoveKey == KeyMap.getKeyCode(EnumKeyFunc.MOVE_LEFT)) {
|
||||
@@ -343,11 +343,11 @@ open class ActorHumanoid(
|
||||
// ↑E, ↓D
|
||||
if (isDownDown && !isUpDown) {
|
||||
walkVertical(false, AXIS_KEYBOARD)
|
||||
prevVMoveKey = AppLoader.getConfigInt("config_keydown")
|
||||
prevVMoveKey = AppLoader.getConfigInt("keydown")
|
||||
} // ↓E, ↑D
|
||||
else if (isUpDown && !isDownDown) {
|
||||
walkVertical(true, AXIS_KEYBOARD)
|
||||
prevVMoveKey = AppLoader.getConfigInt("config_keyup")
|
||||
prevVMoveKey = AppLoader.getConfigInt("keyup")
|
||||
} // ↓E, ↓D
|
||||
/*else if (isUpDown && isDownDown) {
|
||||
if (prevVMoveKey == KeyMap.getKeyCode(EnumKeyFunc.MOVE_UP)) {
|
||||
|
||||
@@ -7,11 +7,12 @@ import net.torvald.terrarum.gameactors.AVKey
|
||||
import net.torvald.terrarum.gameactors.Actor
|
||||
import net.torvald.terrarum.gameitem.GameItem
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex.ITEM_DYNAMIC
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex.ITEM_WALLS
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.lock
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIQuickslotBar
|
||||
import java.math.BigInteger
|
||||
import java.util.*
|
||||
import java.util.concurrent.locks.ReentrantLock
|
||||
|
||||
@@ -40,20 +41,23 @@ class ActorInventory(@Transient val actor: Pocketed, var maxCapacity: Int, var c
|
||||
val itemList = ArrayList<InventoryPair>()
|
||||
val quickSlot = Array<ItemID?>(UIQuickslotBar.SLOT_COUNT) { null } // 0: Slot 1, 9: Slot 10
|
||||
|
||||
var wallet = BigInteger("0") // unified currency for whole civs; Dwarf Fortress approach seems too complicated
|
||||
var wallet = 0 // unified currency for whole civs; Dwarf Fortress approach seems too complicated
|
||||
|
||||
init {
|
||||
}
|
||||
|
||||
fun add(itemID: ItemID, count: Int = 1) {
|
||||
if (ItemCodex[itemID] == null)
|
||||
throw NullPointerException("Item not found: $itemID")
|
||||
else
|
||||
add(ItemCodex[itemID]!!, count)
|
||||
}
|
||||
fun add(itemID: ItemID, count: Int = 1) = add(ItemCodex[itemID]!!, count)
|
||||
fun add(item: GameItem, count: Int = 1) {
|
||||
|
||||
println("[ActorInventory] add-by-elem $item, $count")
|
||||
println("[ActorInventory] add $item, $count")
|
||||
|
||||
|
||||
// not wall-able walls
|
||||
if (item.inventoryCategory == GameItem.Category.WALL &&
|
||||
!BlockCodex[item.dynamicID - ITEM_WALLS.start].isWallable) {
|
||||
throw IllegalArgumentException("Wall ID ${item.dynamicID - ITEM_WALLS.start} is not wall-able.")
|
||||
}
|
||||
|
||||
|
||||
// other invalid values
|
||||
if (count == 0)
|
||||
@@ -61,12 +65,12 @@ class ActorInventory(@Transient val actor: Pocketed, var maxCapacity: Int, var c
|
||||
if (count < 0)
|
||||
throw IllegalArgumentException("Item count is negative number. If you intended removing items, use remove()\n" +
|
||||
"These commands are NOT INTERCHANGEABLE; they handle things differently according to the context.")
|
||||
if (item.originalID == "actor:${Terrarum.PLAYER_REF_ID}" || item.originalID == ("actor:${0x51621D}")) // do not delete this magic
|
||||
if (item.originalID == Terrarum.PLAYER_REF_ID || item.originalID == 0x51621D) // do not delete this magic
|
||||
throw IllegalArgumentException("Attempted to put human player into the inventory.")
|
||||
if (((Terrarum.ingame as? TerrarumIngame)?.gameFullyLoaded ?: false) &&
|
||||
(item.originalID == "actor:${(Terrarum.ingame as? TerrarumIngame)?.actorNowPlaying?.referenceID}"))
|
||||
(item.originalID == (Terrarum.ingame as? TerrarumIngame)?.actorNowPlaying?.referenceID))
|
||||
throw IllegalArgumentException("Attempted to put active player into the inventory.")
|
||||
if ((!item.stackable || item.dynamicID.startsWith("dyn:")) && count > 1)
|
||||
if ((!item.stackable || item.dynamicID in ITEM_DYNAMIC) && count > 1)
|
||||
throw IllegalArgumentException("Attempting to adding stack of item but the item is not stackable; item: $item, count: $count")
|
||||
|
||||
|
||||
|
||||
@@ -14,15 +14,15 @@ import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
open class DroppedItem(private val item: GameItem) : ActorWithBody(RenderOrder.MIDTOP, PhysProperties.PHYSICS_OBJECT) {
|
||||
|
||||
init {
|
||||
if (item.dynamicID.startsWith("actor@"))
|
||||
if (item.dynamicID >= ItemCodex.ACTORID_MIN)
|
||||
throw RuntimeException("Attempted to create DroppedItem actor of a real actor; the real actor must be dropped instead.")
|
||||
|
||||
isVisible = true
|
||||
|
||||
avBaseMass = if (item.dynamicID.startsWith("item@"))
|
||||
ItemCodex[item.dynamicID]!!.mass
|
||||
avBaseMass = if (item.dynamicID < BlockCodex.MAX_TERRAIN_TILES)
|
||||
BlockCodex[item.dynamicID].density / 1000.0
|
||||
else
|
||||
BlockCodex[item.dynamicID].density / 1000.0 // block and wall
|
||||
ItemCodex[item.dynamicID]!!.mass
|
||||
|
||||
actorValue[AVKey.SCALE] = ItemCodex[item.dynamicID]!!.scale
|
||||
}
|
||||
|
||||
@@ -7,7 +7,6 @@ import net.torvald.terrarum.blockproperties.Block
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.gameactors.ActorWithBody
|
||||
import net.torvald.terrarum.gameactors.PhysProperties
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
|
||||
@@ -78,10 +77,10 @@ open class FixtureBase(
|
||||
// if the collision type is allow_move_down, only the top surface tile should be "the platform"
|
||||
// lower part must not have such property (think of the table!)
|
||||
// TODO does this ACTUALLY work ?!
|
||||
world.setTileTerrain(x, y, if (y == posY) BlockBox.ALLOW_MOVE_DOWN else BlockBox.NO_COLLISION, false)
|
||||
world.setTileTerrain(x, y, if (y == posY) BlockBox.ALLOW_MOVE_DOWN else BlockBox.NO_COLLISION)
|
||||
}
|
||||
else
|
||||
world.setTileTerrain(x, y, blockBox.collisionType, false)
|
||||
world.setTileTerrain(x, y, blockBox.collisionType)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -116,7 +115,7 @@ open class FixtureBase(
|
||||
// remove filler block
|
||||
for (x in posX until posX + blockBox.width) {
|
||||
for (y in posY until posY + blockBox.height) {
|
||||
world.setTileTerrain(x, y, Block.AIR, false)
|
||||
world.setTileTerrain(x, y, Block.AIR)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -157,7 +156,7 @@ open class FixtureBase(
|
||||
for (x in posX until posX + blockBox.width) {
|
||||
for (y in posY until posY + blockBox.height) {
|
||||
if (world.getTileFromTerrain(x, y) == blockBox.collisionType) {
|
||||
world.setTileTerrain(x, y, Block.AIR, false)
|
||||
world.setTileTerrain(x, y, Block.AIR)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -202,7 +201,7 @@ inline class BlockBoxProps(val flags: Int) {
|
||||
* @param width Width of the block box, tile-wise
|
||||
* @param height Height of the block box, tile-wise
|
||||
*/
|
||||
data class BlockBox(val collisionType: ItemID, val width: Int, val height: Int) {
|
||||
data class BlockBox(val collisionType: Int, val width: Int, val height: Int) {
|
||||
|
||||
/*fun redefine(collisionType: Int, width: Int, height: Int) {
|
||||
redefine(collisionType)
|
||||
|
||||
@@ -27,7 +27,7 @@ open class HumanoidNPC(
|
||||
}
|
||||
|
||||
// we're having GameItem data so that this class could be somewhat universal
|
||||
override var itemData: GameItem = object : GameItem("actor:"+referenceID) {//GameItem(referenceID ?: forceAssignRefID!!) {
|
||||
override var itemData: GameItem = object : GameItem(referenceID) {//GameItem(referenceID ?: forceAssignRefID!!) {
|
||||
override val isUnique = true
|
||||
override var baseMass: Double
|
||||
get() = actorValue.getAsDouble(AVKey.BASEMASS)!!
|
||||
|
||||
@@ -77,22 +77,20 @@ object PlayerBuilderSigrid {
|
||||
|
||||
CreateTileAtlas.tags.forEach { t, _ ->
|
||||
inventory.add(t, 9995)
|
||||
try {
|
||||
inventory.add("wall@"+t, 9995) // this code will try to add nonexisting wall items, do not get surprised with NPEs
|
||||
}
|
||||
catch (e: Throwable) {
|
||||
System.err.println("[PlayerBuilder] $e")
|
||||
if (BlockCodex[t].isWallable) {
|
||||
inventory.add(t + 4096, 9995)
|
||||
}
|
||||
}
|
||||
|
||||
// item ids are defined in <module>/items/itemid.csv
|
||||
|
||||
inventory.add("item@basegame:1", 16) // copper pick
|
||||
inventory.add("item@basegame:2") // iron pick
|
||||
inventory.add("item@basegame:3") // steel pick
|
||||
inventory.add("item@basegame:4", 9995) // wire piece
|
||||
inventory.add("item@basegame:5", 385930603) // test tiki torch
|
||||
inventory.add("item@basegame:6", 95) // crafting table
|
||||
|
||||
inventory.add(8448, 16) // copper pick
|
||||
inventory.add(8449) // iron pick
|
||||
inventory.add(8450) // steel pick
|
||||
inventory.add(8466, 9995) // wire piece
|
||||
inventory.add(8467, 385930603) // test tiki torch
|
||||
inventory.add(8468, 95) // crafting table
|
||||
inventory.add(9000) // TEST water bucket
|
||||
inventory.add(9001) // TEST lava bucket
|
||||
}
|
||||
}
|
||||
|
||||
@@ -77,12 +77,12 @@ interface Pocketed {
|
||||
}
|
||||
fun equipped(itemID: ItemID) = equipped(ItemCodex[itemID]!!)
|
||||
|
||||
fun addItem(itemID: ItemID, count: Int = 1) = inventory.add(ItemCodex[itemID]!!, count)
|
||||
fun addItem(itemID: Int, count: Int = 1) = inventory.add(ItemCodex[itemID]!!, count)
|
||||
fun addItem(item: GameItem, count: Int = 1) = inventory.add(item, count)
|
||||
fun removeItem(itemID: ItemID, count: Int = 1) = inventory.remove(ItemCodex[itemID]!!, count)
|
||||
fun removeItem(itemID: Int, count: Int = 1) = inventory.remove(ItemCodex[itemID]!!, count)
|
||||
fun removeItem(item: GameItem, count: Int = 1) = inventory.remove(item, count)
|
||||
|
||||
fun hasItem(item: GameItem) = inventory.contains(item.dynamicID)
|
||||
fun hasItem(id: ItemID) = inventory.contains(id)
|
||||
fun hasItem(id: Int) = inventory.contains(id)
|
||||
|
||||
}
|
||||
@@ -3,13 +3,12 @@ package net.torvald.terrarum.modulebasegame.gameactors
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import java.util.concurrent.Callable
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-05-25.
|
||||
*/
|
||||
class ThreadActorUpdate(val startIndex: Int, val endIndex: Int) : Callable<Unit> {
|
||||
override fun call() {
|
||||
class ThreadActorUpdate(val startIndex: Int, val endIndex: Int) : Runnable {
|
||||
override fun run() {
|
||||
for (i in startIndex..endIndex) {
|
||||
val it = Terrarum.ingame!!.actorContainerActive[i]
|
||||
it.update(AppLoader.UPDATE_RATE)
|
||||
|
||||
@@ -5,7 +5,6 @@ import net.torvald.terrarum.Point2i
|
||||
import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.gameactors.ActorWithBody
|
||||
import net.torvald.terrarum.gameitem.GameItem
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
@@ -21,7 +20,7 @@ object BlockBase {
|
||||
* @param dontEncaseActors when set to true, blocks won't be placed where Actors are. You will want to set it false
|
||||
* for wire items, otherwise you want it to be true.
|
||||
*/
|
||||
fun blockStartPrimaryUse(gameItem: GameItem, itemID: ItemID, delta: Float): Boolean {
|
||||
fun blockStartPrimaryUse(gameItem: GameItem, itemID: Int, delta: Float): Boolean {
|
||||
val ingame = Terrarum.ingame!! as TerrarumIngame
|
||||
val mousePoint = Point2d(Terrarum.mouseTileX.toDouble(), Terrarum.mouseTileY.toDouble())
|
||||
val mouseTile = Point2i(Terrarum.mouseTileX, Terrarum.mouseTileY)
|
||||
@@ -46,26 +45,24 @@ object BlockBase {
|
||||
if (gameItem.inventoryCategory == GameItem.Category.BLOCK &&
|
||||
gameItem.dynamicID == ingame.world.getTileFromTerrain(mouseTile.x, mouseTile.y) ||
|
||||
gameItem.inventoryCategory == GameItem.Category.WALL &&
|
||||
gameItem.dynamicID == ingame.world.getTileFromWall(mouseTile.x, mouseTile.y)
|
||||
)
|
||||
gameItem.dynamicID - ItemCodex.ITEM_WALLS.start == ingame.world.getTileFromWall(mouseTile.x, mouseTile.y)
|
||||
)
|
||||
return false
|
||||
|
||||
// filter passed, do the job
|
||||
// FIXME this is only useful for Player
|
||||
if (itemID.startsWith("wall@")) {
|
||||
ingame.world.setTileWall(
|
||||
mouseTile.x,
|
||||
mouseTile.y,
|
||||
itemID.substring(5),
|
||||
false
|
||||
)
|
||||
}
|
||||
else {
|
||||
if (itemID in ItemCodex.ITEM_TILES) {
|
||||
ingame.world.setTileTerrain(
|
||||
mouseTile.x,
|
||||
mouseTile.y,
|
||||
itemID,
|
||||
false
|
||||
itemID
|
||||
)
|
||||
}
|
||||
else {
|
||||
ingame.world.setTileWall(
|
||||
mouseTile.x,
|
||||
mouseTile.y,
|
||||
itemID
|
||||
)
|
||||
}
|
||||
|
||||
@@ -77,8 +74,7 @@ object BlockBase {
|
||||
}
|
||||
|
||||
fun wireStartPrimaryUse(gameItem: GameItem, wireTypeBit: Int, delta: Float): Boolean {
|
||||
return false // TODO need new wire storing format
|
||||
/*val ingame = Terrarum.ingame!! as TerrarumIngame
|
||||
val ingame = Terrarum.ingame!! as TerrarumIngame
|
||||
val mouseTile = Point2i(Terrarum.mouseTileX, Terrarum.mouseTileY)
|
||||
|
||||
// return false if the tile is already there
|
||||
@@ -97,7 +93,7 @@ object BlockBase {
|
||||
)
|
||||
)
|
||||
|
||||
return true*/
|
||||
return true
|
||||
}
|
||||
|
||||
fun wireEffectWhenEquipped(typebit: Int, delta: Float) {
|
||||
|
||||
@@ -7,14 +7,12 @@ import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.blockproperties.Fluid
|
||||
import net.torvald.terrarum.gameactors.ActorWithBody
|
||||
import net.torvald.terrarum.gamecontroller.KeyToggler
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.FluidType
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.ActorHumanoid
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas.TILE_SIZE
|
||||
import org.khelekore.prtree.*
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-08-03.
|
||||
@@ -79,8 +77,8 @@ object WorldSimulator {
|
||||
//printdbg(this, "============================")
|
||||
|
||||
if (player != null) {
|
||||
updateXFrom = player.hitbox.centeredX.div(CreateTileAtlas.TILE_SIZE).minus(FLUID_UPDATING_SQUARE_RADIUS).roundToInt()
|
||||
updateYFrom = player.hitbox.centeredY.div(CreateTileAtlas.TILE_SIZE).minus(FLUID_UPDATING_SQUARE_RADIUS).roundToInt()
|
||||
updateXFrom = player.hitbox.centeredX.div(CreateTileAtlas.TILE_SIZE).minus(FLUID_UPDATING_SQUARE_RADIUS).roundInt()
|
||||
updateYFrom = player.hitbox.centeredY.div(CreateTileAtlas.TILE_SIZE).minus(FLUID_UPDATING_SQUARE_RADIUS).roundInt()
|
||||
updateXTo = updateXFrom + DOUBLE_RADIUS
|
||||
updateYTo = updateYFrom + DOUBLE_RADIUS
|
||||
}
|
||||
@@ -208,8 +206,8 @@ object WorldSimulator {
|
||||
// process the gradual falling of the selected "stack"
|
||||
if (!fallableStackProcessed && fallDownCounter != 0 && isFallable) {
|
||||
// replace blocks
|
||||
world.setTileTerrain(x, y, Block.AIR, true)
|
||||
world.setTileTerrain(x, y + fallDownCounter, currentTile, true)
|
||||
world.setTileTerrain(x, y, Block.AIR)
|
||||
world.setTileTerrain(x, y + fallDownCounter, currentTile)
|
||||
|
||||
fallableStackProcessed = true
|
||||
}
|
||||
@@ -380,8 +378,8 @@ object WorldSimulator {
|
||||
private val FALLABLE_MAX_FALL_SPEED = 2
|
||||
|
||||
private fun monitorIllegalFluidSetup() {
|
||||
for (y in fluidMap.indices) {
|
||||
for (x in fluidMap[0].indices) {
|
||||
for (y in 0 until fluidMap.size) {
|
||||
for (x in 0 until fluidMap[0].size) {
|
||||
val fluidData = world.getFluid(x + updateXFrom, y + updateYFrom)
|
||||
if (fluidData.amount < 0f) {
|
||||
throw InternalError("Negative amount of fluid at (${x + updateXFrom},${y + updateYFrom}): $fluidData")
|
||||
@@ -393,8 +391,8 @@ object WorldSimulator {
|
||||
private fun makeFluidMapFromWorld() {
|
||||
//printdbg(this, "Scan area: ($updateXFrom,$updateYFrom)..(${updateXFrom + fluidMap[0].size},${updateYFrom + fluidMap.size})")
|
||||
|
||||
for (y in fluidMap.indices) {
|
||||
for (x in fluidMap[0].indices) {
|
||||
for (y in 0 until fluidMap.size) {
|
||||
for (x in 0 until fluidMap[0].size) {
|
||||
val fluidData = world.getFluid(x + updateXFrom, y + updateYFrom)
|
||||
fluidMap[y][x] = fluidData.amount
|
||||
fluidTypeMap[y][x] = fluidData.type
|
||||
@@ -409,15 +407,15 @@ object WorldSimulator {
|
||||
}
|
||||
|
||||
private fun fluidmapToWorld() {
|
||||
for (y in fluidMap.indices) {
|
||||
for (x in fluidMap[0].indices) {
|
||||
for (y in 0 until fluidMap.size) {
|
||||
for (x in 0 until fluidMap[0].size) {
|
||||
world.setFluid(x + updateXFrom, y + updateYFrom, fluidNewTypeMap[y][x], fluidNewMap[y][x])
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
fun ItemID.isFallable() = BlockCodex[this].maxSupport
|
||||
fun Int.isFallable() = BlockCodex[this].maxSupport
|
||||
|
||||
|
||||
private val actorMBRConverter = object : MBRConverter<ActorWithBody> {
|
||||
@@ -438,12 +436,14 @@ object WorldSimulator {
|
||||
}
|
||||
|
||||
// simple euclidean norm, squared
|
||||
private val actorDistanceCalculator = DistanceCalculator<ActorWithBody> { t: ActorWithBody, p: PointND ->
|
||||
val dist1 = (p.getOrd(0) - t.hitbox.centeredX).sqr() + (p.getOrd(1) - t.hitbox.centeredY).sqr()
|
||||
// ROUNDWORLD implementation
|
||||
val dist2 = (p.getOrd(0) - (t.hitbox.centeredX - world.width * TILE_SIZE)).sqr() + (p.getOrd(1) - t.hitbox.centeredY).sqr()
|
||||
val dist3 = (p.getOrd(0) - (t.hitbox.centeredX + world.width * TILE_SIZE)).sqr() + (p.getOrd(1) - t.hitbox.centeredY).sqr()
|
||||
private val actorDistanceCalculator = object : DistanceCalculator<ActorWithBody> {
|
||||
override fun distanceTo(t: ActorWithBody, p: PointND): Double {
|
||||
val dist1 = (p.getOrd(0) - t.hitbox.centeredX).sqr() + (p.getOrd(1) - t.hitbox.centeredY).sqr()
|
||||
// ROUNDWORLD implementation
|
||||
val dist2 = (p.getOrd(0) - (t.hitbox.centeredX - world.width * TILE_SIZE)).sqr() + (p.getOrd(1) - t.hitbox.centeredY).sqr()
|
||||
val dist3 = (p.getOrd(0) - (t.hitbox.centeredX + world.width * TILE_SIZE)).sqr() + (p.getOrd(1) - t.hitbox.centeredY).sqr()
|
||||
|
||||
minOf(dist1, minOf(dist2, dist3))
|
||||
return minOf(dist1, minOf(dist2, dist3))
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -96,20 +96,20 @@ class WorldTime(initTime: Long = 0L) {
|
||||
|
||||
|
||||
// these functions won't need inlining for performance
|
||||
val ordinalDay: Int // 0 - 119
|
||||
val yearlyDays: Int // 0 - 119
|
||||
get() = (TIME_T.div(DAY_LENGTH) fmod YEAR_DAYS.toLong()).toInt()
|
||||
val calendarDay: Int // 1 - 30 fixed
|
||||
get() = (ordinalDay % MONTH_LENGTH) + 1
|
||||
val calendarMonth: Int // 1 - 4
|
||||
get() = (ordinalDay / MONTH_LENGTH) + 1
|
||||
val days: Int // 1 - 30 fixed
|
||||
get() = (yearlyDays % MONTH_LENGTH) + 1
|
||||
val months: Int // 1 - 4
|
||||
get() = (yearlyDays / MONTH_LENGTH) + 1
|
||||
val years: Int
|
||||
get() = TIME_T.div(YEAR_DAYS * DAY_LENGTH).abs().toInt() + EPOCH_YEAR
|
||||
|
||||
val quarter = calendarMonth - 1 // 0 - 3
|
||||
val quarter = months - 1 // 0 - 3
|
||||
|
||||
|
||||
val dayOfWeek: Int //0: Mondag-The first day of weekday (0 - 7)
|
||||
get() = if (ordinalDay == YEAR_DAYS - 1) 7 else ordinalDay % 7
|
||||
get() = if (yearlyDays == YEAR_DAYS - 1) 7 else yearlyDays % 7
|
||||
|
||||
var timeDelta: Int = 1
|
||||
set(value) {
|
||||
@@ -206,17 +206,17 @@ class WorldTime(initTime: Long = 0L) {
|
||||
fun getFormattedTime() = "${getDayNameShort()}, " +
|
||||
"$years " +
|
||||
"${getMonthNameFull()} " +
|
||||
"$calendarDay " +
|
||||
"$days " +
|
||||
"${String.format("%02d", hours)}:" +
|
||||
"${String.format("%02d", minutes)}:" +
|
||||
"${String.format("%02d", seconds)}"
|
||||
fun getShortTime() = "${years.toString().padStart(4, '0')}-${getMonthNameShort()}-${calendarDay.toString().padStart(2, '0')}"
|
||||
fun getFilenameTime() = "${years.toString().padStart(4, '0')}${calendarMonth.toString().padStart(2, '0')}${calendarDay.toString().padStart(2, '0')}"
|
||||
fun getShortTime() = "${years.toString().padStart(4, '0')}-${getMonthNameShort()}-${days.toString().padStart(2, '0')}"
|
||||
fun getFilenameTime() = "${years.toString().padStart(4, '0')}${months.toString().padStart(2, '0')}${days.toString().padStart(2, '0')}"
|
||||
|
||||
fun getDayNameFull() = DAY_NAMES[dayOfWeek]
|
||||
fun getDayNameShort() = DAY_NAMES_SHORT[dayOfWeek]
|
||||
fun getMonthNameFull() = MONTH_NAMES[calendarMonth - 1]
|
||||
fun getMonthNameShort() = MONTH_NAMES_SHORT[calendarMonth - 1]
|
||||
fun getMonthNameFull() = MONTH_NAMES[months - 1]
|
||||
fun getMonthNameShort() = MONTH_NAMES_SHORT[months - 1]
|
||||
|
||||
override fun toString() = getFormattedTime()
|
||||
}
|
||||
@@ -38,7 +38,7 @@ class UIBasicInfo(private val player: ActorHumanoid?) : UICanvas() {
|
||||
ELuptimer += delta
|
||||
}
|
||||
|
||||
if (mouseUp || Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyinteract"))) {
|
||||
if (mouseUp || Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyinteract"))) {
|
||||
ELuptimer = 0f
|
||||
ELon = true
|
||||
}
|
||||
|
||||
@@ -157,10 +157,10 @@ package net.torvald.terrarum.modulebasegame.ui
|
||||
private var isEncumbered = false
|
||||
|
||||
|
||||
private val seekLeft: Int; get() = AppLoader.getConfigInt("config_keyleft") // getter used to support in-game keybind changing
|
||||
private val seekRight: Int; get() = AppLoader.getConfigInt("config_keyright") // getter used to support in-game keybind changing
|
||||
private val seekUp: Int; get() = AppLoader.getConfigInt("config_keyup") // getter used to support in-game keybind changing
|
||||
private val seekDown: Int; get() = AppLoader.getConfigInt("config_keydown") // getter used to support in-game keybind changing
|
||||
private val seekLeft: Int; get() = AppLoader.getConfigInt("keyleft") // getter used to support in-game keybind changing
|
||||
private val seekRight: Int; get() = AppLoader.getConfigInt("keyright") // getter used to support in-game keybind changing
|
||||
private val seekUp: Int; get() = AppLoader.getConfigInt("keyup") // getter used to support in-game keybind changing
|
||||
private val seekDown: Int; get() = AppLoader.getConfigInt("keydown") // getter used to support in-game keybind changing
|
||||
|
||||
|
||||
init {
|
||||
@@ -307,7 +307,7 @@ package net.torvald.terrarum.modulebasegame.ui
|
||||
inventorySortList.sortBy { it.item.name }
|
||||
|
||||
// map sortList to item list
|
||||
for (k in items.indices) {
|
||||
for (k in 0 until items.size) {
|
||||
// we have an item
|
||||
try {
|
||||
val sortListItem = inventorySortList[k + itemPage * items.size]
|
||||
|
||||
@@ -7,7 +7,6 @@ import net.torvald.terrarum.*
|
||||
import net.torvald.terrarum.gameactors.ActorWithBody
|
||||
import net.torvald.terrarum.langpack.Lang
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.ActorInventory
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIInventoryFull.Companion.INVEN_DEBUG_MODE
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
@@ -32,8 +31,8 @@ internal class UIInventoryCells(
|
||||
UIItemInventoryDynamicList(
|
||||
full,
|
||||
full.actor.inventory,
|
||||
full.INVENTORY_CELLS_OFFSET_X,
|
||||
full.INVENTORY_CELLS_OFFSET_Y,
|
||||
0 + (AppLoader.screenW - full.internalWidth) / 2,
|
||||
107 + (AppLoader.screenH - full.internalHeight) / 2,
|
||||
full.CELLS_HOR, full.CELLS_VRT
|
||||
)
|
||||
|
||||
@@ -44,7 +43,7 @@ internal class UIInventoryCells(
|
||||
full.actor.inventory,
|
||||
full.actor as ActorWithBody,
|
||||
full.internalWidth - UIItemInventoryEquippedView.WIDTH + (AppLoader.screenW - full.internalWidth) / 2,
|
||||
full.INVENTORY_CELLS_OFFSET_Y
|
||||
107 + (AppLoader.screenH - full.internalHeight) / 2
|
||||
)
|
||||
|
||||
init {
|
||||
@@ -123,7 +122,7 @@ internal class UIInventoryCells(
|
||||
)
|
||||
// debug text
|
||||
batch.color = Color.LIGHT_GRAY
|
||||
if (INVEN_DEBUG_MODE) {
|
||||
if (AppLoader.IS_DEVELOPMENT_BUILD) {
|
||||
AppLoader.fontSmallNumbers.draw(batch,
|
||||
"${full.actor.inventory.capacity}/${full.actor.inventory.maxCapacity}",
|
||||
encumbBarTextXPos,
|
||||
|
||||
@@ -1,76 +0,0 @@
|
||||
package net.torvald.terrarum.modulebasegame.ui
|
||||
|
||||
import com.badlogic.gdx.Gdx
|
||||
import com.badlogic.gdx.graphics.Camera
|
||||
import com.badlogic.gdx.graphics.Color
|
||||
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.TitleScreen
|
||||
import net.torvald.terrarum.blendNormal
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
import net.torvald.terrarum.ui.UIItemTextButtonList
|
||||
import net.torvald.terrarum.ui.UIItemTextButtonList.Companion.DEFAULT_LINE_HEIGHT
|
||||
|
||||
class UIInventoryEscMenu(val full: UIInventoryFull) : UICanvas() {
|
||||
|
||||
override var width: Int = AppLoader.screenW
|
||||
override var height: Int = AppLoader.screenH
|
||||
override var openCloseTime = 0.0f
|
||||
|
||||
private val gameMenu = arrayOf("MENU_LABEL_MAINMENU", "MENU_LABEL_DESKTOP", "MENU_OPTIONS_CONTROLS", "MENU_OPTIONS_SOUND", "MENU_LABEL_GRAPHICS")
|
||||
private val gameMenuListHeight = DEFAULT_LINE_HEIGHT * gameMenu.size
|
||||
private val gameMenuListWidth = 400
|
||||
private val gameMenuButtons = UIItemTextButtonList(
|
||||
this, gameMenu,
|
||||
(AppLoader.screenW - gameMenuListWidth) / 2,
|
||||
full.INVENTORY_CELLS_OFFSET_Y + (full.INVENTORY_CELLS_UI_HEIGHT - gameMenuListHeight) / 2,
|
||||
gameMenuListWidth, gameMenuListHeight,
|
||||
readFromLang = true,
|
||||
textAreaWidth = gameMenuListWidth,
|
||||
activeBackCol = Color(0),
|
||||
highlightBackCol = Color(0),
|
||||
backgroundCol = Color(0),
|
||||
inactiveCol = Color.WHITE,
|
||||
defaultSelection = null
|
||||
)
|
||||
|
||||
init {
|
||||
uiItems.add(gameMenuButtons)
|
||||
|
||||
gameMenuButtons.selectionChangeListener = { _, new ->
|
||||
when (new) {
|
||||
0 -> AppLoader.setScreen(TitleScreen(AppLoader.batch))
|
||||
1 -> Gdx.app.exit()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun updateUI(delta: Float) {
|
||||
gameMenuButtons.update(delta)
|
||||
}
|
||||
|
||||
override fun renderUI(batch: SpriteBatch, camera: Camera) {
|
||||
// control hints
|
||||
blendNormal(batch)
|
||||
batch.color = Color.WHITE
|
||||
AppLoader.fontGame.draw(batch, full.gameMenuControlHelp, full.offsetX, full.yEnd - 20)
|
||||
|
||||
// text buttons
|
||||
gameMenuButtons.render(batch, camera)
|
||||
}
|
||||
|
||||
override fun doOpening(delta: Float) {
|
||||
}
|
||||
|
||||
override fun doClosing(delta: Float) {
|
||||
}
|
||||
|
||||
override fun endOpening(delta: Float) {
|
||||
}
|
||||
|
||||
override fun endClosing(delta: Float) {
|
||||
}
|
||||
|
||||
override fun dispose() {
|
||||
}
|
||||
}
|
||||
@@ -29,14 +29,16 @@ class UIInventoryFull(
|
||||
doNotWarnConstant: Boolean = false
|
||||
) : UICanvas(toggleKeyLiteral, toggleButtonLiteral, customPositioning, doNotWarnConstant) {
|
||||
|
||||
private val debugvals = true
|
||||
|
||||
override var width: Int = AppLoader.screenW
|
||||
override var height: Int = AppLoader.screenH
|
||||
override var openCloseTime: Second = 0.0f
|
||||
|
||||
val REQUIRED_MARGIN: Int = 138 // hard-coded value. Don't know the details. Range: [91-146]. I chose MAX-8 because cell gap is 8
|
||||
val REQUIRED_MARGIN = 166 // hard-coded value. Don't know the details
|
||||
|
||||
val CELLS_HOR = 10
|
||||
val CELLS_VRT: Int; get() = (AppLoader.screenH - REQUIRED_MARGIN - 134 + UIItemInventoryDynamicList.listGap) / // 134 is another magic number
|
||||
val CELLS_VRT = (AppLoader.screenH - REQUIRED_MARGIN - 134 + UIItemInventoryDynamicList.listGap) / // 134 is another magic number
|
||||
(UIItemInventoryElemSimple.height + UIItemInventoryDynamicList.listGap)
|
||||
|
||||
private val itemListToEquipViewGap = UIItemInventoryDynamicList.listGap // used to be 24; figured out that the extra gap does nothig
|
||||
@@ -46,10 +48,6 @@ class UIInventoryFull(
|
||||
|
||||
val itemListHeight: Int = CELLS_VRT * UIItemInventoryElemSimple.height + (CELLS_VRT - 1) * net.torvald.terrarum.modulebasegame.ui.UIItemInventoryDynamicList.Companion.listGap
|
||||
|
||||
val INVENTORY_CELLS_UI_HEIGHT: Int = CELLS_VRT * UIItemInventoryElemSimple.height + (CELLS_VRT - 1) * UIItemInventoryDynamicList.listGap
|
||||
val INVENTORY_CELLS_OFFSET_X = 0 + (AppLoader.screenW - internalWidth) / 2
|
||||
val INVENTORY_CELLS_OFFSET_Y: Int = 107 + (AppLoader.screenH - internalHeight) / 2
|
||||
|
||||
init {
|
||||
handler.allowESCtoClose = true
|
||||
CommonResourcePool.addToLoadingList("inventory_caticons") {
|
||||
@@ -113,13 +111,13 @@ class UIInventoryFull(
|
||||
)
|
||||
|
||||
|
||||
private val transitionalMinimap = UIInventoryMinimap(this) // PLACEHOLDER
|
||||
private val transitionalMinimap = UIInventoryCells(this) // PLACEHOLDER
|
||||
private val transitionalItemCells = UIInventoryCells(this)
|
||||
private val transitionalEscMenu = UIInventoryEscMenu(this)
|
||||
private val transitionalEscMenu = UIInventoryCells(this) // PLACEHOLDER
|
||||
private val transitionPanel = UIItemHorizontalFadeSlide(
|
||||
this,
|
||||
(AppLoader.screenW - internalWidth) / 2,
|
||||
INVENTORY_CELLS_OFFSET_Y,
|
||||
107 + (AppLoader.screenH - internalHeight) / 2,
|
||||
AppLoader.screenW,
|
||||
AppLoader.screenH,
|
||||
1f,
|
||||
@@ -127,9 +125,36 @@ class UIInventoryFull(
|
||||
)
|
||||
|
||||
|
||||
private val gameMenu = arrayOf("MENU_LABEL_MAINMENU", "MENU_LABEL_DESKTOP", "MENU_OPTIONS_CONTROLS", "MENU_OPTIONS_SOUND", "MENU_LABEL_GRAPHICS")
|
||||
private val gameMenuListHeight = DEFAULT_LINE_HEIGHT * gameMenu.size
|
||||
private val gameMenuListWidth = 400
|
||||
private val gameMenuButtons = UIItemTextButtonList(
|
||||
this, gameMenu,
|
||||
(AppLoader.screenW - gameMenuListWidth) / 2,
|
||||
(transitionalItemCells.itemList.height - gameMenuListHeight) / 2 + transitionalItemCells.itemList.posY,
|
||||
gameMenuListWidth, gameMenuListHeight,
|
||||
readFromLang = true,
|
||||
textAreaWidth = gameMenuListWidth,
|
||||
activeBackCol = Color(0),
|
||||
highlightBackCol = Color(0),
|
||||
backgroundCol = Color(0),
|
||||
inactiveCol = Color.WHITE,
|
||||
defaultSelection = null
|
||||
)
|
||||
|
||||
private val SCREEN_MINIMAP = 0f
|
||||
private val SCREEN_INVENTORY = 1f
|
||||
private val SCREEN_MENU = 2f
|
||||
|
||||
|
||||
|
||||
|
||||
init {
|
||||
addUIitem(categoryBar)
|
||||
addUIitem(transitionPanel)
|
||||
//itemList.let { addUIitem(it) }
|
||||
//equipped.let { addUIitem(it) }
|
||||
|
||||
|
||||
categoryBar.selectionChangeListener = { old, new ->
|
||||
rebuildList()
|
||||
@@ -139,6 +164,15 @@ class UIInventoryFull(
|
||||
|
||||
rebuildList()
|
||||
|
||||
// make gameMenuButtons work
|
||||
gameMenuButtons.selectionChangeListener = { old, new ->
|
||||
if (new == 0) {
|
||||
AppLoader.setScreen(TitleScreen(AppLoader.batch))
|
||||
}
|
||||
else if (new == 1) {
|
||||
Gdx.app.exit()
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -154,8 +188,29 @@ class UIInventoryFull(
|
||||
rebuildList()
|
||||
}
|
||||
|
||||
|
||||
categoryBar.update(delta)
|
||||
transitionPanel.update(delta)
|
||||
|
||||
|
||||
// update map while visible
|
||||
/*if (currentScreenTransition > 1f + epsilon) {
|
||||
MinimapComposer.setWorld(Terrarum.ingame!!.world)
|
||||
MinimapComposer.update()
|
||||
}*/
|
||||
|
||||
// update inventory while visible
|
||||
/*if (currentScreenTransition in epsilon..2f - epsilon) {
|
||||
itemList.update(delta)
|
||||
equipped.update(delta)
|
||||
}*/
|
||||
|
||||
// update menu while visible
|
||||
/*if (currentScreenTransition < 1f - epsilon) {
|
||||
gameMenuButtons.update(delta)
|
||||
}*/
|
||||
|
||||
minimapRerenderTimer += Gdx.graphics.rawDeltaTime
|
||||
}
|
||||
|
||||
private val gradStartCol = Color(0x404040_60)
|
||||
@@ -168,6 +223,18 @@ class UIInventoryFull(
|
||||
internal var yEnd = (AppLoader.screenH + internalHeight).div(2).toFloat()
|
||||
private set
|
||||
|
||||
private var minimapRerenderTimer = 0f
|
||||
private val minimapRerenderInterval = .5f
|
||||
|
||||
// TODO implemented on UIItemTransitionContainer
|
||||
/*fun requestTransition(target: Int) {
|
||||
if (!transitionOngoing) {
|
||||
transitionRequested = true
|
||||
transitionReqSource = currentScreenTransition.round()
|
||||
transitionReqTarget = target.toFloat()
|
||||
}
|
||||
}*/
|
||||
|
||||
override fun renderUI(batch: SpriteBatch, camera: Camera) {
|
||||
|
||||
|
||||
@@ -195,8 +262,252 @@ class UIInventoryFull(
|
||||
// UI items
|
||||
categoryBar.render(batch, camera)
|
||||
transitionPanel.render(batch, camera)
|
||||
|
||||
// render map while visible
|
||||
/*if (currentScreenTransition > 1f + epsilon) {
|
||||
renderScreenMinimap(batch, camera)
|
||||
|
||||
if (debugvals) {
|
||||
batch.color = Color.CORAL
|
||||
AppLoader.fontSmallNumbers.draw(batch, "Map", 300f, 10f)
|
||||
}
|
||||
}*/
|
||||
|
||||
// render inventory while visible
|
||||
/*if (currentScreenTransition in epsilon..2f - epsilon) {
|
||||
renderScreenInventory(batch, camera)
|
||||
|
||||
if (debugvals) {
|
||||
batch.color = Color.CHARTREUSE
|
||||
AppLoader.fontSmallNumbers.draw(batch, "Inv", 350f, 10f)
|
||||
}
|
||||
}*/
|
||||
|
||||
// render menu while visible
|
||||
/*if (currentScreenTransition < 1f - epsilon) {
|
||||
renderScreenGamemenu(batch, camera)
|
||||
|
||||
if (debugvals) {
|
||||
batch.color = Color.SKY
|
||||
AppLoader.fontSmallNumbers.draw(batch, "Men", 400f, 10f)
|
||||
}
|
||||
}*/
|
||||
|
||||
/*if (debugvals) {
|
||||
batch.color = Color.WHITE
|
||||
AppLoader.fontSmallNumbers.draw(batch, "minimap:$minimapScrOffX", 500f, 0f)
|
||||
AppLoader.fontSmallNumbers.draw(batch, "inven:$inventoryScrOffX", 500f, 10f)
|
||||
AppLoader.fontSmallNumbers.draw(batch, "menu:$menuScrOffX", 500f, 20f)
|
||||
}*/
|
||||
|
||||
|
||||
}
|
||||
|
||||
private val epsilon = 0.001f
|
||||
|
||||
/**
|
||||
* - 0 on inventory screen
|
||||
* - +WIDTH on minimap screen
|
||||
* - -WIDTH on gamemenu screen
|
||||
*/
|
||||
/*private val minimapScrOffX: Float
|
||||
get() = (currentScreenTransition - 2f) * AppLoader.screenW / 2f
|
||||
private val inventoryScrOffX: Float
|
||||
get() = (currentScreenTransition - 1f) * AppLoader.screenW / 2f
|
||||
private val menuScrOffX: Float
|
||||
get() = (currentScreenTransition - 0f) * AppLoader.screenW / 2f
|
||||
|
||||
private val minimapScrOpacity: Float
|
||||
get() = (currentScreenTransition - 2f).coerceIn(0f, 1f)
|
||||
private val inventoryScrOpacity: Float
|
||||
get() = (currentScreenTransition - 1f).coerceIn(0f, 1f)
|
||||
private val menuScrOpacity: Float
|
||||
get() = (currentScreenTransition - 0f).coerceIn(0f, 1f)*/
|
||||
|
||||
//private val MINIMAP_WIDTH = 800f
|
||||
//private val MINIMAP_HEIGHT = itemList.height.toFloat()
|
||||
//private val MINIMAP_SKYCOL = Color(0x88bbddff.toInt())
|
||||
//private var minimapZoom = 1f
|
||||
//private var minimapPanX = -MinimapComposer.totalWidth / 2f
|
||||
//private var minimapPanY = -MinimapComposer.totalHeight / 2f
|
||||
//private val MINIMAP_ZOOM_MIN = 0.5f
|
||||
//private val MINIMAP_ZOOM_MAX = 8f
|
||||
//private val minimapFBO = FrameBuffer(Pixmap.Format.RGBA8888, MINIMAP_WIDTH.toInt(), MINIMAP_HEIGHT.toInt(), false)
|
||||
//private val minimapCamera = OrthographicCamera(MINIMAP_WIDTH, MINIMAP_HEIGHT)
|
||||
|
||||
|
||||
// TODO put 3 bare sub-UIs into proper UIcanvas to handle the motherfucking opacity
|
||||
|
||||
// TODO not yet refactored
|
||||
/*private fun renderScreenMinimap(batch: SpriteBatch, camera: Camera) {
|
||||
blendNormal(batch)
|
||||
|
||||
// update map panning
|
||||
if (currentScreenTransition >= 2f - epsilon) {
|
||||
// if left click is down and cursor is in the map area
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("mouseprimary")) &&
|
||||
Terrarum.mouseScreenY in itemList.posY..itemList.posY + itemList.height) {
|
||||
minimapPanX += Terrarum.mouseDeltaX / minimapZoom
|
||||
minimapPanY += Terrarum.mouseDeltaY / minimapZoom
|
||||
}
|
||||
|
||||
|
||||
if (Gdx.input.isKeyPressed(Input.Keys.NUM_1)) {
|
||||
minimapZoom *= (1f / 1.02f)
|
||||
}
|
||||
if (Gdx.input.isKeyPressed(Input.Keys.NUM_2)) {
|
||||
minimapZoom *= 1.02f
|
||||
}
|
||||
if (Gdx.input.isKeyPressed(Input.Keys.NUM_3)) {
|
||||
minimapZoom = 1f
|
||||
minimapPanX = -MinimapComposer.totalWidth / 2f
|
||||
minimapPanY = -MinimapComposer.totalHeight / 2f
|
||||
}
|
||||
|
||||
|
||||
try {
|
||||
//minimapPanX = minimapPanX.coerceIn(-(MinimapComposer.totalWidth * minimapZoom) + MINIMAP_WIDTH, 0f) // un-comment this line to constain the panning over x-axis
|
||||
} catch (e: IllegalArgumentException) { }
|
||||
try {
|
||||
//minimapPanY = minimapPanY.coerceIn(-(MinimapComposer.totalHeight * minimapZoom) + MINIMAP_HEIGHT, 0f)
|
||||
} catch (e: IllegalArgumentException) { }
|
||||
minimapZoom = minimapZoom.coerceIn(MINIMAP_ZOOM_MIN, MINIMAP_ZOOM_MAX)
|
||||
|
||||
|
||||
// make image to roll over for x-axis. This is for the ROUNDWORLD implementation, feel free to remove below.
|
||||
|
||||
}
|
||||
|
||||
|
||||
// render minimap
|
||||
batch.end()
|
||||
|
||||
if (minimapRerenderTimer >= minimapRerenderInterval) {
|
||||
minimapRerenderTimer = 0f
|
||||
MinimapComposer.requestRender()
|
||||
}
|
||||
|
||||
MinimapComposer.renderToBackground()
|
||||
|
||||
minimapFBO.inAction(minimapCamera, batch) {
|
||||
// whatever.
|
||||
MinimapComposer.tempTex.dispose()
|
||||
MinimapComposer.tempTex = Texture(MinimapComposer.minimap)
|
||||
MinimapComposer.tempTex.setFilter(Texture.TextureFilter.Linear, Texture.TextureFilter.Nearest)
|
||||
|
||||
batch.inUse {
|
||||
|
||||
// [ 1 0 0 ] [ s 0 0 ] [ s 0 0 ]
|
||||
// [ 0 1 0 ] x [ 0 s 0 ] = [ 0 s 0 ]
|
||||
// [ px py 1 ] [ w/2 h/2 1 ] [ tx ty 1 ]
|
||||
//
|
||||
// https://www.wolframalpha.com/input/?i=%7B%7B1,0,0%7D,%7B0,1,0%7D,%7Bp_x,p_y,1%7D%7D+*+%7B%7Bs,0,0%7D,%7B0,s,0%7D,%7Bw%2F2,h%2F2,1%7D%7D
|
||||
|
||||
val tx = minimapPanX * minimapZoom + 0.5f * MINIMAP_WIDTH
|
||||
val ty = minimapPanY * minimapZoom + 0.5f * MINIMAP_HEIGHT
|
||||
|
||||
// sky background
|
||||
batch.color = MINIMAP_SKYCOL
|
||||
batch.fillRect(0f, 0f, MINIMAP_WIDTH, MINIMAP_HEIGHT)
|
||||
// the actual image
|
||||
batch.color = Color.WHITE
|
||||
batch.draw(MinimapComposer.tempTex, tx, ty + MinimapComposer.totalHeight * minimapZoom, MinimapComposer.totalWidth * minimapZoom, -MinimapComposer.totalHeight * minimapZoom)
|
||||
|
||||
}
|
||||
}
|
||||
batch.begin()
|
||||
|
||||
if (debugvals) {
|
||||
AppLoader.fontSmallNumbers.draw(batch, "$minimapPanX, $minimapPanY; x$minimapZoom", minimapScrOffX + (AppLoader.screenW - MINIMAP_WIDTH) / 2, -10f + itemList.posY)
|
||||
}
|
||||
|
||||
batch.projectionMatrix = camera.combined
|
||||
// 1px stroke
|
||||
batch.color = Color.WHITE
|
||||
batch.fillRect(-1 + minimapScrOffX + (AppLoader.screenW - MINIMAP_WIDTH) / 2, -1 + itemList.posY.toFloat(), 2 + MINIMAP_WIDTH, 2 + MINIMAP_HEIGHT)
|
||||
|
||||
// control hints
|
||||
batch.color = Color.WHITE
|
||||
AppLoader.fontGame.draw(batch, minimapControlHelp, offsetX + minimapScrOffX, yEnd - 20)
|
||||
|
||||
// the minimap
|
||||
batch.draw(minimapFBO.colorBufferTexture, minimapScrOffX + (AppLoader.screenW - MINIMAP_WIDTH) / 2, itemList.posY.toFloat())
|
||||
}*/
|
||||
|
||||
// TODO not yet refactored
|
||||
/*private fun renderScreenGamemenu(batch: SpriteBatch, camera: Camera) {
|
||||
// control hints
|
||||
blendNormal(batch)
|
||||
batch.color = Color.WHITE
|
||||
AppLoader.fontGame.draw(batch, gameMenuControlHelp, offsetX + menuScrOffX, yEnd - 20)
|
||||
|
||||
// text buttons
|
||||
gameMenuButtons.posX = gameMenuButtons.initialX + menuScrOffX.roundToInt()
|
||||
gameMenuButtons.render(batch, camera)
|
||||
}*/
|
||||
|
||||
// TODO refactoring wip
|
||||
/*private fun renderScreenInventory(batch: SpriteBatch, camera: Camera) {
|
||||
itemList.posX = itemList.initialX + inventoryScrOffX.roundToInt()
|
||||
itemList.render(batch, camera)
|
||||
equipped.posX = equipped.initialX + inventoryScrOffX.roundToInt()
|
||||
equipped.render(batch, camera)
|
||||
|
||||
|
||||
// control hints
|
||||
val controlHintXPos = offsetX + inventoryScrOffX
|
||||
blendNormal(batch)
|
||||
batch.color = Color.WHITE
|
||||
AppLoader.fontGame.draw(batch, listControlHelp, controlHintXPos, yEnd - 20)
|
||||
|
||||
|
||||
// encumbrance meter
|
||||
val encumbranceText = Lang["GAME_INVENTORY_ENCUMBRANCE"]
|
||||
// encumbrance bar will go one row down if control help message is too long
|
||||
val encumbBarXPos = xEnd - weightBarWidth + inventoryScrOffX
|
||||
val encumbBarTextXPos = encumbBarXPos - 6 - AppLoader.fontGame.getWidth(encumbranceText)
|
||||
val encumbBarYPos = yEnd-20 + 3f +
|
||||
if (AppLoader.fontGame.getWidth(listControlHelp) + 2 + controlHintXPos >= encumbBarTextXPos)
|
||||
AppLoader.fontGame.lineHeight
|
||||
else 0f
|
||||
|
||||
AppLoader.fontGame.draw(batch,
|
||||
encumbranceText,
|
||||
encumbBarTextXPos,
|
||||
encumbBarYPos - 3f
|
||||
)
|
||||
|
||||
// encumbrance bar background
|
||||
blendNormal(batch)
|
||||
val encumbCol = UIItemInventoryCellCommonRes.getHealthMeterColour(1f - encumbrancePerc, 0f, 1f)
|
||||
val encumbBack = encumbCol mul UIItemInventoryCellCommonRes.meterBackDarkening
|
||||
batch.color = encumbBack
|
||||
batch.fillRect(
|
||||
encumbBarXPos, encumbBarYPos,
|
||||
weightBarWidth, controlHelpHeight - 6f
|
||||
)
|
||||
// encumbrance bar
|
||||
batch.color = encumbCol
|
||||
batch.fillRect(
|
||||
encumbBarXPos, encumbBarYPos,
|
||||
if (actor.inventory.capacityMode == CAPACITY_MODE_NO_ENCUMBER)
|
||||
1f
|
||||
else // make sure 1px is always be seen
|
||||
minOf(weightBarWidth, maxOf(1f, weightBarWidth * encumbrancePerc)),
|
||||
controlHelpHeight - 6f
|
||||
)
|
||||
// debug text
|
||||
batch.color = Color.LIGHT_GRAY
|
||||
if (IS_DEVELOPMENT_BUILD) {
|
||||
AppLoader.fontSmallNumbers.draw(batch,
|
||||
"${actor.inventory.capacity}/${actor.inventory.maxCapacity}",
|
||||
encumbBarTextXPos,
|
||||
encumbBarYPos + controlHelpHeight - 4f
|
||||
)
|
||||
}
|
||||
}*/
|
||||
|
||||
|
||||
fun rebuildList() {
|
||||
transitionalItemCells.rebuildList()
|
||||
}
|
||||
@@ -253,9 +564,5 @@ class UIInventoryFull(
|
||||
xEnd = (AppLoader.screenW + internalWidth).div(2).toFloat()
|
||||
yEnd = (AppLoader.screenH + internalHeight).div(2).toFloat()
|
||||
}
|
||||
|
||||
companion object {
|
||||
const val INVEN_DEBUG_MODE = false
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,146 +0,0 @@
|
||||
package net.torvald.terrarum.modulebasegame.ui
|
||||
|
||||
import com.badlogic.gdx.Gdx
|
||||
import com.badlogic.gdx.Input
|
||||
import com.badlogic.gdx.graphics.*
|
||||
import com.badlogic.gdx.graphics.g2d.SpriteBatch
|
||||
import com.badlogic.gdx.graphics.glutils.FrameBuffer
|
||||
import net.torvald.terrarum.*
|
||||
import net.torvald.terrarum.blockstats.MinimapComposer
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
|
||||
class UIInventoryMinimap(val full: UIInventoryFull) : UICanvas() {
|
||||
|
||||
private val debugvals = true
|
||||
|
||||
override var width: Int = AppLoader.screenW
|
||||
override var height: Int = AppLoader.screenH
|
||||
override var openCloseTime = 0.0f
|
||||
|
||||
private val MINIMAP_WIDTH = 800f
|
||||
private val MINIMAP_HEIGHT = full.INVENTORY_CELLS_UI_HEIGHT.toFloat()
|
||||
private val MINIMAP_SKYCOL = Color(0x88bbddff.toInt())
|
||||
private var minimapZoom = 1f
|
||||
private var minimapPanX = -MinimapComposer.totalWidth / 2f
|
||||
private var minimapPanY = -MinimapComposer.totalHeight / 2f
|
||||
private val MINIMAP_ZOOM_MIN = 0.5f
|
||||
private val MINIMAP_ZOOM_MAX = 8f
|
||||
private val minimapFBO = FrameBuffer(Pixmap.Format.RGBA8888, MINIMAP_WIDTH.toInt(), MINIMAP_HEIGHT.toInt(), false)
|
||||
private val minimapCamera = OrthographicCamera(MINIMAP_WIDTH, MINIMAP_HEIGHT)
|
||||
|
||||
private var minimapRerenderTimer = 0f
|
||||
private val minimapRerenderInterval = .5f
|
||||
|
||||
override fun updateUI(delta: Float) {
|
||||
MinimapComposer.setWorld(Terrarum.ingame!!.world)
|
||||
MinimapComposer.update()
|
||||
minimapRerenderTimer += Gdx.graphics.rawDeltaTime
|
||||
}
|
||||
|
||||
override fun renderUI(batch: SpriteBatch, camera: Camera) {
|
||||
blendNormal(batch)
|
||||
|
||||
// update map panning
|
||||
// if left click is down and cursor is in the map area
|
||||
if (Gdx.input.isButtonPressed(AppLoader.getConfigInt("config_mouseprimary")) &&
|
||||
Terrarum.mouseScreenY in full.INVENTORY_CELLS_OFFSET_Y..full.INVENTORY_CELLS_OFFSET_Y + full.INVENTORY_CELLS_UI_HEIGHT) {
|
||||
minimapPanX += Terrarum.mouseDeltaX * 2f / minimapZoom
|
||||
minimapPanY += Terrarum.mouseDeltaY * 2f / minimapZoom
|
||||
}
|
||||
|
||||
|
||||
if (Gdx.input.isKeyPressed(Input.Keys.NUM_1)) {
|
||||
minimapZoom *= (1f / 1.02f)
|
||||
}
|
||||
if (Gdx.input.isKeyPressed(Input.Keys.NUM_2)) {
|
||||
minimapZoom *= 1.02f
|
||||
}
|
||||
if (Gdx.input.isKeyPressed(Input.Keys.NUM_3)) {
|
||||
minimapZoom = 1f
|
||||
minimapPanX = -MinimapComposer.totalWidth / 2f
|
||||
minimapPanY = -MinimapComposer.totalHeight / 2f
|
||||
}
|
||||
|
||||
|
||||
try {
|
||||
//minimapPanX = minimapPanX.coerceIn(-(MinimapComposer.totalWidth * minimapZoom) + MINIMAP_WIDTH, 0f) // un-comment this line to constain the panning over x-axis
|
||||
} catch (e: IllegalArgumentException) { }
|
||||
try {
|
||||
//minimapPanY = minimapPanY.coerceIn(-(MinimapComposer.totalHeight * minimapZoom) + MINIMAP_HEIGHT, 0f)
|
||||
} catch (e: IllegalArgumentException) { }
|
||||
minimapZoom = minimapZoom.coerceIn(MINIMAP_ZOOM_MIN, MINIMAP_ZOOM_MAX)
|
||||
|
||||
|
||||
// make image to roll over for x-axis. This is for the ROUNDWORLD implementation, feel free to remove below.
|
||||
|
||||
|
||||
// render minimap
|
||||
batch.end()
|
||||
|
||||
if (minimapRerenderTimer >= minimapRerenderInterval) {
|
||||
minimapRerenderTimer = 0f
|
||||
MinimapComposer.requestRender()
|
||||
}
|
||||
|
||||
MinimapComposer.renderToBackground()
|
||||
|
||||
minimapFBO.inAction(minimapCamera, batch) {
|
||||
// whatever.
|
||||
MinimapComposer.tempTex.dispose()
|
||||
MinimapComposer.tempTex = Texture(MinimapComposer.minimap)
|
||||
MinimapComposer.tempTex.setFilter(Texture.TextureFilter.Linear, Texture.TextureFilter.Nearest)
|
||||
|
||||
batch.inUse {
|
||||
|
||||
// [ 1 0 0 ] [ s 0 0 ] [ s 0 0 ]
|
||||
// [ 0 1 0 ] x [ 0 s 0 ] = [ 0 s 0 ]
|
||||
// [ px py 1 ] [ w/2 h/2 1 ] [ tx ty 1 ]
|
||||
//
|
||||
// https://www.wolframalpha.com/input/?i=%7B%7B1,0,0%7D,%7B0,1,0%7D,%7Bp_x,p_y,1%7D%7D+*+%7B%7Bs,0,0%7D,%7B0,s,0%7D,%7Bw%2F2,h%2F2,1%7D%7D
|
||||
|
||||
val tx = minimapPanX * minimapZoom + 0.5f * MINIMAP_WIDTH
|
||||
val ty = minimapPanY * minimapZoom + 0.5f * MINIMAP_HEIGHT
|
||||
|
||||
// sky background
|
||||
batch.color = MINIMAP_SKYCOL
|
||||
batch.fillRect(0f, 0f, MINIMAP_WIDTH, MINIMAP_HEIGHT)
|
||||
// the actual image
|
||||
batch.color = Color.WHITE
|
||||
batch.draw(MinimapComposer.tempTex, tx, ty + MinimapComposer.totalHeight * minimapZoom, MinimapComposer.totalWidth * minimapZoom, -MinimapComposer.totalHeight * minimapZoom)
|
||||
|
||||
}
|
||||
}
|
||||
batch.begin()
|
||||
|
||||
if (debugvals) {
|
||||
AppLoader.fontSmallNumbers.draw(batch, "$minimapPanX, $minimapPanY; x$minimapZoom", (AppLoader.screenW - MINIMAP_WIDTH) / 2, -10f + full.INVENTORY_CELLS_OFFSET_Y)
|
||||
}
|
||||
|
||||
batch.projectionMatrix = camera.combined
|
||||
// 1px stroke
|
||||
batch.color = Color.WHITE
|
||||
batch.fillRect((AppLoader.screenW - MINIMAP_WIDTH) / 2, -1 + full.INVENTORY_CELLS_OFFSET_Y.toFloat(), MINIMAP_WIDTH, 1f)
|
||||
batch.fillRect((AppLoader.screenW - MINIMAP_WIDTH) / 2, full.INVENTORY_CELLS_OFFSET_Y + MINIMAP_HEIGHT, MINIMAP_WIDTH, 1f)
|
||||
batch.fillRect(-1 + (AppLoader.screenW - MINIMAP_WIDTH) / 2, full.INVENTORY_CELLS_OFFSET_Y.toFloat(), 1f, MINIMAP_HEIGHT)
|
||||
batch.fillRect((AppLoader.screenW - MINIMAP_WIDTH) / 2 + MINIMAP_WIDTH, full.INVENTORY_CELLS_OFFSET_Y.toFloat(), 1f, MINIMAP_HEIGHT)
|
||||
|
||||
// control hints
|
||||
batch.color = Color.WHITE
|
||||
AppLoader.fontGame.draw(batch, full.minimapControlHelp, full.offsetX, full.yEnd - 20)
|
||||
|
||||
// the minimap
|
||||
batch.draw(minimapFBO.colorBufferTexture, (AppLoader.screenW - MINIMAP_WIDTH) / 2, full.INVENTORY_CELLS_OFFSET_Y.toFloat())
|
||||
}
|
||||
|
||||
override fun doOpening(delta: Float) {}
|
||||
|
||||
override fun doClosing(delta: Float) {}
|
||||
|
||||
override fun endOpening(delta: Float) {}
|
||||
|
||||
override fun endClosing(delta: Float) {}
|
||||
|
||||
override fun dispose() {
|
||||
minimapFBO.dispose()
|
||||
}
|
||||
}
|
||||
@@ -11,7 +11,6 @@ import net.torvald.terrarum.modulebasegame.gameactors.ActorInventory
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.InventoryPair
|
||||
import net.torvald.terrarum.modulebasegame.ui.ItemSlotImageFactory.CELLCOLOUR_BLACK
|
||||
import net.torvald.terrarum.modulebasegame.ui.ItemSlotImageFactory.CELLCOLOUR_BLACK_ACTIVE
|
||||
import net.torvald.terrarum.modulebasegame.ui.UIInventoryFull.Companion.INVEN_DEBUG_MODE
|
||||
import net.torvald.terrarum.ui.UIItem
|
||||
import net.torvald.terrarum.ui.UIItemImageButton
|
||||
import net.torvald.terrarum.ui.UIItemTextButton.Companion.defaultActiveCol
|
||||
@@ -310,7 +309,7 @@ class UIItemInventoryDynamicList(
|
||||
// set tooltip accordingly
|
||||
if (isCompactMode && it.item != null && it.mouseUp && !tooltipSet) {
|
||||
(Terrarum.ingame as? TerrarumIngame)?.setTooltipMessage(
|
||||
if (INVEN_DEBUG_MODE) {
|
||||
if (AppLoader.IS_DEVELOPMENT_BUILD) {
|
||||
it.item?.name + "/Mat: ${it.item?.material?.identifier}"
|
||||
}
|
||||
else {
|
||||
@@ -354,7 +353,7 @@ class UIItemInventoryDynamicList(
|
||||
inventorySortList.sortBy { ItemCodex[it.item]!!.name }
|
||||
|
||||
// map sortList to item list
|
||||
for (k in items.indices) {
|
||||
for (k in 0 until items.size) {
|
||||
// we have an item
|
||||
try {
|
||||
val sortListItem = inventorySortList[k + itemPage * items.size]
|
||||
@@ -373,7 +372,7 @@ class UIItemInventoryDynamicList(
|
||||
}
|
||||
|
||||
// set equippedslot number
|
||||
for (eq in inventory.itemEquipped.indices) {
|
||||
for (eq in 0 until inventory.itemEquipped.size) {
|
||||
if (eq < inventory.itemEquipped.size) {
|
||||
if (inventory.itemEquipped[eq] == items[k].item?.dynamicID) {
|
||||
items[k].equippedSlot = eq
|
||||
|
||||
@@ -118,7 +118,7 @@ class UIItemInventoryEquippedView(
|
||||
// sort by equip position
|
||||
|
||||
// fill the grid from fastest index, make no gap in-between of slots
|
||||
for (k in itemGrid.indices) {
|
||||
for (k in 0 until itemGrid.size) {
|
||||
val item = inventory.itemEquipped[k]
|
||||
|
||||
if (item == null) {
|
||||
|
||||
@@ -9,7 +9,6 @@ import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.blendNormal
|
||||
import net.torvald.terrarum.blockproperties.Block
|
||||
import net.torvald.terrarum.fillRect
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulebasegame.BuildingMaker
|
||||
import net.torvald.terrarum.modulebasegame.ui.ItemSlotImageFactory.CELLCOLOUR_BLACK
|
||||
@@ -32,8 +31,8 @@ class UIPaletteSelector(val parent: BuildingMaker) : UICanvas() {
|
||||
fun mouseOnTitleBar() =
|
||||
relativeMouseX in 0 until width && relativeMouseY in 0 until LINE_HEIGHT
|
||||
|
||||
var fore: ItemID = Block.STONE_BRICKS
|
||||
var back: ItemID = Block.GLASS_CRUDE
|
||||
var fore = Block.STONE_BRICKS
|
||||
var back = Block.GLASS_CRUDE
|
||||
|
||||
private val titleText = "Pal."
|
||||
|
||||
@@ -103,9 +102,10 @@ class UIPaletteSelector(val parent: BuildingMaker) : UICanvas() {
|
||||
}
|
||||
|
||||
fun swapForeAndBack() {
|
||||
val t = fore
|
||||
fore = back
|
||||
back = t
|
||||
// xor used, because why not?
|
||||
fore = fore xor back
|
||||
back = back xor fore
|
||||
fore = fore xor back
|
||||
}
|
||||
|
||||
override fun doOpening(delta: Float) {
|
||||
|
||||
@@ -16,7 +16,7 @@ import net.torvald.terrarum.ui.UICanvas
|
||||
* Created by minjaesong on 2019-08-11.
|
||||
*/
|
||||
class UIScreenZoom : UICanvas(
|
||||
AppLoader.getConfigInt("config_keyzoom")
|
||||
AppLoader.getConfigInt("keyzoom")
|
||||
) {
|
||||
|
||||
val zoomText = "${keyToIcon(handler.toggleKeyLiteral!!)} $EMDASH Zoom Out"
|
||||
|
||||
@@ -11,7 +11,6 @@ import net.torvald.terrarum.modulebasegame.gameworld.WorldTime
|
||||
import net.torvald.terrarum.modulebasegame.imagefont.WatchFont
|
||||
import net.torvald.terrarum.ui.UICanvas
|
||||
import net.torvald.terrarumsansbitmap.gdx.TextureRegionPack
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2017-06-11.
|
||||
@@ -47,7 +46,7 @@ class UITierOneWatch(private val player: ActorHumanoid?) : UICanvas() {
|
||||
ELuptimer += delta
|
||||
}
|
||||
|
||||
if (mouseUp || Gdx.input.isKeyPressed(AppLoader.getConfigInt("config_keyinteract"))) {
|
||||
if (mouseUp || Gdx.input.isKeyPressed(AppLoader.getConfigInt("keyinteract"))) {
|
||||
ELuptimer = 0f
|
||||
ELon = true
|
||||
}
|
||||
@@ -77,7 +76,7 @@ class UITierOneWatch(private val player: ActorHumanoid?) : UICanvas() {
|
||||
watchFont.draw(batch, worldTime.getDayNameShort().toUpperCase(), 73f, 7f)
|
||||
|
||||
// day
|
||||
watchFont.draw(batch, worldTime.calendarDay.toString().padStart(2, '@'), 107f, 7f)
|
||||
watchFont.draw(batch, worldTime.days.toString().padStart(2, '@'), 107f, 7f)
|
||||
|
||||
// hour
|
||||
watchFont.draw(batch, worldTime.hours.toString().padStart(2, '@'), 27f, 7f)
|
||||
@@ -85,11 +84,11 @@ class UITierOneWatch(private val player: ActorHumanoid?) : UICanvas() {
|
||||
watchFont.draw(batch, worldTime.minutes.toString().padStart(2, '0'), 49f, 7f)
|
||||
|
||||
// season marker
|
||||
batch.draw(atlas.get(1, worldTime.calendarMonth - 1), 0f, 0f)
|
||||
batch.draw(atlas.get(1, worldTime.months - 1), 0f, 0f)
|
||||
|
||||
|
||||
// moon dial
|
||||
val moonPhase = (worldTime.moonPhase * moonDialCount).roundToInt() % moonDialCount
|
||||
val moonPhase = (worldTime.moonPhase * moonDialCount).roundInt() % moonDialCount
|
||||
batch.color = lcdLitCol
|
||||
batch.draw(moonDial.get(moonPhase, 0), 6f, 3f)
|
||||
}
|
||||
|
||||
@@ -16,6 +16,7 @@ import net.torvald.terrarum.modulebasegame.RNGConsumer
|
||||
import net.torvald.terrarum.modulebasegame.TerrarumIngame
|
||||
import net.torvald.terrarum.modulebasegame.gameactors.ParticleMegaRain
|
||||
import net.torvald.terrarum.modulebasegame.gameworld.GameWorldExtension
|
||||
import net.torvald.terrarum.modulebasegame.worldgenerator.WorldGenerator
|
||||
import net.torvald.terrarum.utils.JsonFetcher
|
||||
import net.torvald.terrarum.worlddrawer.CreateTileAtlas
|
||||
import net.torvald.terrarum.worlddrawer.WorldCamera
|
||||
@@ -299,13 +300,13 @@ internal object WeatherMixer : RNGConsumer {
|
||||
|
||||
var mixFrom: String?
|
||||
try { mixFrom = JSON.get("mixFrom").asJsonPrimitive.asString }
|
||||
catch (e: NullPointerException) { mixFrom = null }
|
||||
catch (e: IllegalStateException) { mixFrom = null }
|
||||
|
||||
|
||||
|
||||
var mixPercentage: Double?
|
||||
try { mixPercentage = JSON.get("mixPercentage").asJsonPrimitive.asDouble }
|
||||
catch (e: NullPointerException) { mixPercentage = null }
|
||||
catch (e: IllegalStateException) { mixPercentage = null }
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -23,13 +23,21 @@ class Biomegen(world: GameWorld, seed: Long, params: Any) : Gen(world, seed, par
|
||||
|
||||
private val genSlices = maxOf(ThreadExecutor.threadCount, world.width / 8)
|
||||
|
||||
private var genFutures: Array<Future<*>?> = arrayOfNulls(genSlices)
|
||||
override var generationStarted: Boolean = false
|
||||
override val generationDone: Boolean
|
||||
get() = generationStarted && genFutures.fold(true) { acc, f -> acc and (f?.isDone ?: true) }
|
||||
|
||||
private val YHEIGHT_MAGIC = 2800.0 / 3.0
|
||||
private val YHEIGHT_DIVISOR = 2.0 / 7.0
|
||||
|
||||
override fun getDone() {
|
||||
override fun run() {
|
||||
|
||||
generationStarted = true
|
||||
|
||||
ThreadExecutor.renew()
|
||||
(0 until world.width).sliceEvenly(genSlices).map { xs ->
|
||||
ThreadExecutor.submit {
|
||||
(0 until world.width).sliceEvenly(genSlices).mapIndexed { i, xs ->
|
||||
genFutures[i] = ThreadExecutor.submit {
|
||||
val localJoise = getGenerator(seed, params as BiomegenParams)
|
||||
for (x in xs) {
|
||||
for (y in 0 until world.height) {
|
||||
@@ -86,17 +94,17 @@ class Biomegen(world: GameWorld, seed: Long, params: Any) : Gen(world, seed, par
|
||||
when (control) {
|
||||
0 -> { // woodlands
|
||||
if (tileThis == Block.DIRT && nearbyTerr.any { it == Block.AIR } && nearbyWall.any { it == Block.AIR }) {
|
||||
world.setTileTerrain(x, y, Block.GRASS, true)
|
||||
world.setTileTerrain(x, y, Block.GRASS)
|
||||
}
|
||||
}
|
||||
1 -> { // shrublands
|
||||
if (tileThis == Block.DIRT && nearbyTerr.any { it == Block.AIR } && nearbyWall.any { it == Block.AIR }) {
|
||||
world.setTileTerrain(x, y, Block.GRASS, true)
|
||||
world.setTileTerrain(x, y, Block.GRASS)
|
||||
}
|
||||
}
|
||||
2, 3 -> { // plains
|
||||
if (tileThis == Block.DIRT && nearbyTerr.any { it == Block.AIR } && nearbyWall.any { it == Block.AIR }) {
|
||||
world.setTileTerrain(x, y, Block.GRASS, true)
|
||||
world.setTileTerrain(x, y, Block.GRASS)
|
||||
}
|
||||
}
|
||||
/*3 -> { // sands
|
||||
@@ -109,8 +117,8 @@ class Biomegen(world: GameWorld, seed: Long, params: Any) : Gen(world, seed, par
|
||||
}*/
|
||||
4 -> { // rockylands
|
||||
if (tileThis == Block.DIRT) {
|
||||
world.setTileTerrain(x, y, Block.STONE, true)
|
||||
world.setTileWall(x, y, Block.STONE, true)
|
||||
world.setTileTerrain(x, y, Block.STONE)
|
||||
world.setTileWall(x, y, Block.STONE)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-03-31.
|
||||
*/
|
||||
interface NoiseFilter {
|
||||
fun getGrad(func_argX: Int, start: Double, end: Double): Double
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
import com.jme3.math.FastMath
|
||||
|
||||
/**
|
||||
* Double Quadratic polynomial
|
||||
* (16/9) * (start-end)/height^2 * (x-height)^2 + end
|
||||
* 16/9: terrain is formed from 1/4 of height.
|
||||
* 1 - (1/4) = 3/4, reverse it and square it.
|
||||
* That makes 16/9.
|
||||
|
||||
* Shape:
|
||||
|
||||
* cavity -
|
||||
* small
|
||||
* -
|
||||
* -
|
||||
* --
|
||||
* ----
|
||||
* cavity --------
|
||||
* large ----------------
|
||||
|
||||
* @param func_argX
|
||||
* *
|
||||
* @param start
|
||||
* *
|
||||
* @param end
|
||||
* *
|
||||
* @return
|
||||
* Created by minjaesong on 2016-03-31.
|
||||
*/
|
||||
object NoiseFilterCubic : NoiseFilter {
|
||||
override fun getGrad(func_argX: Int, start: Double, end: Double): Double {
|
||||
val graph_gradient = -FastMath.pow(FastMath.pow((1 - WorldGenerator.TERRAIN_AVERAGE_HEIGHT).toFloat(), 3f), -1f) * // 1/4 -> 3/4 -> 9/16 -> 16/9
|
||||
(start - end) / FastMath.pow(WorldGenerator.HEIGHT.toFloat(), 3f) *
|
||||
FastMath.pow((func_argX - WorldGenerator.HEIGHT).toFloat(), 3f) + end
|
||||
|
||||
if (func_argX < WorldGenerator.TERRAIN_AVERAGE_HEIGHT) {
|
||||
return start
|
||||
} else if (func_argX >= WorldGenerator.HEIGHT) {
|
||||
return end
|
||||
} else {
|
||||
return graph_gradient
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
import com.jme3.math.FastMath
|
||||
|
||||
/**
|
||||
* Quadratic polynomial
|
||||
* -(16/9) * (start-end)/height^2 * (x - 0.25 * height)^2 + start
|
||||
* 16/9: terrain is formed from 1/4 of height.
|
||||
* 1 - (1/4) = 3/4, reverse it and square it.
|
||||
* That makes 16/9.
|
||||
|
||||
* Shape:
|
||||
|
||||
* cavity _
|
||||
* small
|
||||
* _
|
||||
* _
|
||||
* __
|
||||
* ____
|
||||
* cavity ________
|
||||
* large ________________
|
||||
|
||||
* @param func_argX
|
||||
* *
|
||||
* @param start
|
||||
* *
|
||||
* @param end
|
||||
* *
|
||||
* @return
|
||||
* Created by minjaesong on 2016-03-31.
|
||||
*/
|
||||
object NoiseFilterMinusQuadratic : NoiseFilter {
|
||||
override fun getGrad(func_argX: Int, start: Double, end: Double): Double {
|
||||
val graph_gradient = -FastMath.pow(FastMath.sqr((1 - WorldGenerator.TERRAIN_AVERAGE_HEIGHT).toFloat()), -1f) * // 1/4 -> 3/4 -> 9/16 -> 16/9
|
||||
(start - end) / FastMath.sqr(WorldGenerator.HEIGHT.toFloat()) *
|
||||
FastMath.sqr((func_argX - WorldGenerator.TERRAIN_AVERAGE_HEIGHT).toFloat()) + start
|
||||
|
||||
if (func_argX < WorldGenerator.TERRAIN_AVERAGE_HEIGHT) {
|
||||
return start
|
||||
} else if (func_argX >= WorldGenerator.HEIGHT) {
|
||||
return end
|
||||
} else {
|
||||
return graph_gradient
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
import com.jme3.math.FastMath
|
||||
|
||||
/**
|
||||
* Quadratic polynomial
|
||||
* (16/9) * (start-end)/height^2 * (x-height)^2 + end
|
||||
* 16/9: terrain is formed from 1/4 of height.
|
||||
* 1 - (1/4) = 3/4, reverse it and square it.
|
||||
* That makes 16/9.
|
||||
|
||||
* Shape:
|
||||
|
||||
* cavity -
|
||||
* small
|
||||
* -
|
||||
* -
|
||||
* --
|
||||
* ----
|
||||
* cavity --------
|
||||
* large ----------------
|
||||
|
||||
* @param func_argX
|
||||
* *
|
||||
* @param start
|
||||
* *
|
||||
* @param end
|
||||
* *
|
||||
* @return
|
||||
*
|
||||
* Created by minjaesong on 2016-03-31.
|
||||
*/
|
||||
object NoiseFilterQuadratic : NoiseFilter {
|
||||
override fun getGrad(func_argX: Int, start: Double, end: Double): Double {
|
||||
val graph_gradient = FastMath.pow(FastMath.sqr((1 - WorldGenerator.TERRAIN_AVERAGE_HEIGHT).toFloat()), -1f) * // 1/4 -> 3/4 -> 9/16 -> 16/9
|
||||
(start - end) / FastMath.sqr(WorldGenerator.HEIGHT.toFloat()) *
|
||||
FastMath.sqr((func_argX - WorldGenerator.HEIGHT).toFloat()) + end
|
||||
|
||||
if (func_argX < WorldGenerator.TERRAIN_AVERAGE_HEIGHT) {
|
||||
return start
|
||||
} else if (func_argX >= WorldGenerator.HEIGHT) {
|
||||
return end
|
||||
} else {
|
||||
return graph_gradient
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
import com.jme3.math.FastMath
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-03-31.
|
||||
*/
|
||||
object NoiseFilterSqrt : NoiseFilter {
|
||||
override fun getGrad(func_argX: Int, start: Double, end: Double): Double {
|
||||
val graph_gradient = (end - start) / FastMath.sqrt((WorldGenerator.HEIGHT - WorldGenerator.TERRAIN_AVERAGE_HEIGHT).toFloat()) * FastMath.sqrt((func_argX - WorldGenerator.TERRAIN_AVERAGE_HEIGHT).toFloat()) + start
|
||||
|
||||
if (func_argX < WorldGenerator.TERRAIN_AVERAGE_HEIGHT) {
|
||||
return start
|
||||
} else if (func_argX >= WorldGenerator.HEIGHT) {
|
||||
return end
|
||||
} else {
|
||||
return graph_gradient
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-03-31.
|
||||
*/
|
||||
object NoiseFilterUniform : NoiseFilter {
|
||||
override fun getGrad(func_argX: Int, start: Double, end: Double): Double {
|
||||
return 1.0
|
||||
}
|
||||
}
|
||||
@@ -20,30 +20,35 @@ class Terragen(world: GameWorld, seed: Long, params: Any) : Gen(world, seed, par
|
||||
|
||||
private val genSlices = maxOf(ThreadExecutor.threadCount, world.width / 8)
|
||||
|
||||
private var genFutures: Array<Future<*>?> = arrayOfNulls(genSlices)
|
||||
override var generationStarted: Boolean = false
|
||||
override val generationDone: Boolean
|
||||
get() = generationStarted && genFutures.fold(true) { acc, f -> acc and (f?.isDone ?: true) }
|
||||
|
||||
private val YHEIGHT_MAGIC = 2800.0 / 3.0
|
||||
private val YHEIGHT_DIVISOR = 2.0 / 7.0
|
||||
|
||||
override fun getDone() {
|
||||
override fun run() {
|
||||
|
||||
generationStarted = true
|
||||
|
||||
ThreadExecutor.renew()
|
||||
(0 until world.width).sliceEvenly(genSlices).mapIndexed { i, xs ->
|
||||
ThreadExecutor.submit {
|
||||
genFutures[i] = ThreadExecutor.submit {
|
||||
val localJoise = getGenerator(seed, params as TerragenParams)
|
||||
//val localLock = java.lang.Object() // in an attempt to fix the "premature exit" issue of a thread run
|
||||
//synchronized(localLock) { // also see: https://stackoverflow.com/questions/28818494/threads-stopping-prematurely-for-certain-values
|
||||
for (x in xs) {
|
||||
for (y in 0 until world.height) {
|
||||
val sampleTheta = (x.toDouble() / world.width) * TWO_PI
|
||||
val sampleOffset = world.width / 8.0
|
||||
val sampleX = sin(sampleTheta) * sampleOffset + sampleOffset // plus sampleOffset to make only
|
||||
val sampleZ = cos(sampleTheta) * sampleOffset + sampleOffset // positive points are to be sampled
|
||||
val sampleY = y - (world.height - YHEIGHT_MAGIC) * YHEIGHT_DIVISOR // Q&D offsetting to make ratio of sky:ground to be constant
|
||||
// DEBUG NOTE: it is the OFFSET FROM THE IDEAL VALUE (observed land height - (HEIGHT * DIVISOR)) that must be constant
|
||||
val noise = localJoise.map { it.get(sampleX, sampleY, sampleZ) }
|
||||
for (x in xs) {
|
||||
for (y in 0 until world.height) {
|
||||
val sampleTheta = (x.toDouble() / world.width) * TWO_PI
|
||||
val sampleOffset = world.width / 8.0
|
||||
val sampleX = sin(sampleTheta) * sampleOffset + sampleOffset // plus sampleOffset to make only
|
||||
val sampleZ = cos(sampleTheta) * sampleOffset + sampleOffset // positive points are to be sampled
|
||||
val sampleY = y - (world.height - YHEIGHT_MAGIC) * YHEIGHT_DIVISOR // Q&D offsetting to make ratio of sky:ground to be constant
|
||||
// DEBUG NOTE: it is the OFFSET FROM THE IDEAL VALUE (observed land height - (HEIGHT * DIVISOR)) that must be constant
|
||||
val noise = localJoise.map { it.get(sampleX, sampleY, sampleZ) }
|
||||
|
||||
draw(x, y, noise, world)
|
||||
}
|
||||
draw(x, y, noise, world)
|
||||
}
|
||||
//}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -69,10 +74,10 @@ class Terragen(world: GameWorld, seed: Long, params: Any) : Gen(world, seed, par
|
||||
val cave = if (noiseValue[1] < 0.5) 0 else 1
|
||||
|
||||
val wallBlock = groundDepthBlock[terr]
|
||||
val terrBlock = if (cave == 0) Block.AIR else wallBlock //wallBlock * cave // AIR is always zero, this is the standard
|
||||
val terrBlock = wallBlock * cave // AIR is always zero, this is the standard
|
||||
|
||||
world.setTileTerrain(x, y, terrBlock, true)
|
||||
world.setTileWall(x, y, wallBlock, true)
|
||||
world.setTileTerrain(x, y, terrBlock)
|
||||
world.setTileWall(x, y, wallBlock)
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,71 @@
|
||||
package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
|
||||
import net.torvald.terrarum.AppLoader
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2016-06-13.
|
||||
*/
|
||||
class ThreadProcessNoiseLayers(val startIndex: Int, val endIndex: Int,
|
||||
val noiseRecords: Array<WorldGenerator.TaggedJoise>) : Runnable {
|
||||
|
||||
|
||||
override fun run() {
|
||||
for (record in noiseRecords) {
|
||||
println("[mapgenerator] ${record.message}...")
|
||||
AppLoader.getLoadScreen().addMessage("${record.message}...")
|
||||
|
||||
for (y in startIndex..endIndex) {
|
||||
for (x in 0..WorldGenerator.WIDTH - 1) {
|
||||
// straight-line sampling
|
||||
/*val noise: Float = record.noiseModule.get(
|
||||
x.toDouble() / 48.0, // 48: Fixed value
|
||||
y.toDouble() / 48.0
|
||||
).toFloat()*/
|
||||
// circular sampling
|
||||
// Mapping function:
|
||||
// World(x, y) -> Joise(sin x, y, cos x)
|
||||
val sampleDensity = 48.0 / 2 // 48.0: magic number from old code
|
||||
val sampleTheta = (x.toDouble() / WorldGenerator.WIDTH) * WorldGenerator.TWO_PI
|
||||
val sampleOffset = (WorldGenerator.WIDTH / sampleDensity) / 8.0
|
||||
val sampleX = Math.sin(sampleTheta) * sampleOffset + sampleOffset // plus sampleOffset to make only
|
||||
val sampleZ = Math.cos(sampleTheta) * sampleOffset + sampleOffset // positive points are to be sampled
|
||||
val sampleY = y / sampleDensity
|
||||
val noise: Double = record.noiseModule.get(sampleX, sampleY, sampleZ)
|
||||
|
||||
val fromTerr = record.replaceFromTerrain
|
||||
val fromWall = record.replaceFromWall
|
||||
|
||||
val to: Int = when (record.replaceTo) {
|
||||
// replace to designated tile
|
||||
is Int -> record.replaceTo as Int
|
||||
// replace to randomly selected tile from given array of tile IDs
|
||||
is IntArray -> (record.replaceTo as IntArray)[WorldGenerator.random.nextInt((record.replaceTo as IntArray).size)]
|
||||
else -> throw IllegalArgumentException("[mapgenerator] Unknown replaceTo tile type '${record.replaceTo.javaClass.canonicalName}': Only 'kotlin.Int' and 'kotlin.IntArray' is valid.")
|
||||
}
|
||||
// replace to ALL? this is bullshit
|
||||
if (to == WorldGenerator.TILE_MACRO_ALL) throw IllegalArgumentException("[mapgenerator] Invalid replaceTo: TILE_MACRO_ALL")
|
||||
|
||||
// filtered threshold
|
||||
val threshold = record.filter.getGrad(y, record.filterArg1, record.filterArg2)
|
||||
|
||||
if (noise > threshold * record.scarcity) {
|
||||
if (fromTerr is IntArray) {
|
||||
for (i in 0..fromTerr.size - 1) {
|
||||
val fromTerrVariable = fromTerr[i]
|
||||
|
||||
if ((WorldGenerator.world.getTileFromTerrain(x, y) == fromTerrVariable || fromTerrVariable == WorldGenerator.TILE_MACRO_ALL)
|
||||
&& (WorldGenerator.world.getTileFromWall(x, y) == fromWall || fromWall == WorldGenerator.TILE_MACRO_ALL)) {
|
||||
WorldGenerator.world.setTileTerrain(x, y, to)
|
||||
}
|
||||
}
|
||||
}
|
||||
else if ((WorldGenerator.world.getTileFromTerrain(x, y) == fromTerr || fromTerr == WorldGenerator.TILE_MACRO_ALL)
|
||||
&& (WorldGenerator.world.getTileFromWall(x, y) == fromWall || fromWall == WorldGenerator.TILE_MACRO_ALL)) {
|
||||
WorldGenerator.world.setTileTerrain(x, y, to)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -10,8 +10,8 @@ import net.torvald.terrarum.blockproperties.Block
|
||||
import net.torvald.terrarum.blockproperties.BlockCodex
|
||||
import net.torvald.terrarum.concurrent.ThreadParallel
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import net.torvald.terrarum.roundInt
|
||||
import java.util.*
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
@Deprecated("Old non-thread-safe version", ReplaceWith("Terragen", "net.torvald.terrarum.modulebasegame.worldgenerator"))
|
||||
object WorldGenerator {
|
||||
@@ -776,12 +776,12 @@ object WorldGenerator {
|
||||
private fun processNoiseLayers(noiseRecords: Array<TaggedJoise>) {
|
||||
if (AppLoader.MULTITHREAD) {
|
||||
// set up indices
|
||||
for (i in 0 until AppLoader.THREAD_COUNT) {
|
||||
for (i in 0 until AppLoader.THREADS) {
|
||||
ThreadParallel.map(
|
||||
i, "SampleJoiseMap",
|
||||
ThreadProcessNoiseLayers(
|
||||
HEIGHT.toFloat().div(AppLoader.THREAD_COUNT).times(i).roundToInt(),
|
||||
HEIGHT.toFloat().div(AppLoader.THREAD_COUNT).times(i.plus(1)).roundToInt() - 1,
|
||||
HEIGHT.toFloat().div(AppLoader.THREADS).times(i).roundInt(),
|
||||
HEIGHT.toFloat().div(AppLoader.THREADS).times(i.plus(1)).roundInt() - 1,
|
||||
noiseRecords
|
||||
)
|
||||
)
|
||||
@@ -3,7 +3,6 @@ package net.torvald.terrarum.modulebasegame.worldgenerator
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.gameworld.GameWorld
|
||||
import java.util.concurrent.Callable
|
||||
|
||||
/**
|
||||
* New world generator.
|
||||
@@ -13,8 +12,7 @@ import java.util.concurrent.Callable
|
||||
object Worldgen {
|
||||
|
||||
private lateinit var world: GameWorld
|
||||
lateinit var params: WorldgenParams
|
||||
private set
|
||||
private lateinit var params: WorldgenParams
|
||||
|
||||
private val threadLock = java.lang.Object()
|
||||
|
||||
@@ -36,7 +34,7 @@ object Worldgen {
|
||||
val it = jobs[i]
|
||||
|
||||
AppLoader.getLoadScreen().addMessage(it.loadingScreenName)
|
||||
it.theWork.getDone()
|
||||
it.theWork.run()
|
||||
}
|
||||
|
||||
printdbg(this, "Generation job finished")
|
||||
@@ -48,7 +46,9 @@ object Worldgen {
|
||||
}
|
||||
|
||||
abstract class Gen(val world: GameWorld, val seed: Long, val params: Any) {
|
||||
open fun getDone() { } // trying to use different name so that it won't be confused with Runnable or Callable
|
||||
abstract var generationStarted: Boolean
|
||||
abstract val generationDone: Boolean
|
||||
open fun run() { }
|
||||
}
|
||||
|
||||
data class WorldgenParams(
|
||||
|
||||
@@ -366,7 +366,7 @@ class LuaComputerVM(val display: MDA) {
|
||||
if (sine > 0.79) sine = 0.79
|
||||
else if (sine < -0.79) sine = -0.79
|
||||
audioData.put(
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundToInt().toByte()
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundInt().toByte()
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -377,7 +377,7 @@ class LuaComputerVM(val display: MDA) {
|
||||
sine += Math.sin(Math.PI * 2 * (2*k - 1) * chopSize * x) / (2*k - 1)
|
||||
}
|
||||
audioData.put(
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundToInt().toByte()
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundInt().toByte()
|
||||
)
|
||||
}
|
||||
}*/
|
||||
|
||||
@@ -509,7 +509,7 @@ class TerrarumComputerOldOld(peripheralSlots: Int) {
|
||||
if (sine > 0.79) sine = 0.79
|
||||
else if (sine < -0.79) sine = -0.79
|
||||
audioData.put(
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundToInt().toByte()
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundInt().toByte()
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -520,7 +520,7 @@ class TerrarumComputerOldOld(peripheralSlots: Int) {
|
||||
sine += Math.sin(Math.PI * 2 * (2*k - 1) * chopSize * x) / (2*k - 1)
|
||||
}
|
||||
audioData.put(
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundToInt().toByte()
|
||||
(0.5 + 0.5 * sine).times(0xFF).roundInt().toByte()
|
||||
)
|
||||
}
|
||||
}*/
|
||||
|
||||
@@ -2,7 +2,6 @@ package net.torvald.terrarum.serialise
|
||||
|
||||
import com.badlogic.gdx.utils.compression.Lzma
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.BlockAddress
|
||||
import net.torvald.terrarum.gameworld.BlockLayer
|
||||
import net.torvald.terrarum.gameworld.FluidType
|
||||
@@ -152,10 +151,9 @@ internal object ReadLayerDataLzma {
|
||||
val wallDamages = HashMap<BlockAddress, Float>()
|
||||
val fluidTypes = HashMap<BlockAddress, FluidType>()
|
||||
val fluidFills = HashMap<BlockAddress, Float>()
|
||||
val tileNumToName = HashMap<Int, ItemID>()
|
||||
|
||||
// parse terrain damages
|
||||
for (c in payloadBytes["TdMG"]!!.indices step 10) {
|
||||
for (c in 0 until payloadBytes["TdMG"]!!.size step 10) {
|
||||
val bytes = payloadBytes["TdMG"]!!
|
||||
|
||||
val tileAddr = bytes.sliceArray(c..c+5)
|
||||
@@ -166,7 +164,7 @@ internal object ReadLayerDataLzma {
|
||||
|
||||
|
||||
// parse wall damages
|
||||
for (c in payloadBytes["WdMG"]!!.indices step 10) {
|
||||
for (c in 0 until payloadBytes["WdMG"]!!.size step 10) {
|
||||
val bytes = payloadBytes["WdMG"]!!
|
||||
|
||||
val tileAddr = bytes.sliceArray(c..c+5)
|
||||
@@ -178,8 +176,6 @@ internal object ReadLayerDataLzma {
|
||||
|
||||
// TODO parse fluid(Types|Fills)
|
||||
|
||||
// TODO parse tileNumToName
|
||||
|
||||
|
||||
return ReadLayerDataZip.LayerData(
|
||||
BlockLayer(width, height, payloadBytes["WALL"]!!),
|
||||
@@ -187,7 +183,7 @@ internal object ReadLayerDataLzma {
|
||||
|
||||
spawnPoint.first, spawnPoint.second,
|
||||
|
||||
wallDamages, terrainDamages, fluidTypes, fluidFills, tileNumToName
|
||||
wallDamages, terrainDamages, fluidTypes, fluidFills
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
package net.torvald.terrarum.serialise
|
||||
|
||||
import net.torvald.terrarum.AppLoader.printdbg
|
||||
import net.torvald.terrarum.gameitem.ItemID
|
||||
import net.torvald.terrarum.gameworld.BlockAddress
|
||||
import net.torvald.terrarum.gameworld.BlockLayer
|
||||
import net.torvald.terrarum.gameworld.FluidType
|
||||
@@ -153,10 +152,9 @@ internal object ReadLayerDataZip {
|
||||
val wallDamages = HashMap<BlockAddress, Float>()
|
||||
val fluidTypes = HashMap<BlockAddress, FluidType>()
|
||||
val fluidFills = HashMap<BlockAddress, Float>()
|
||||
val tileNumberToNameMap = HashMap<Int, ItemID>()
|
||||
|
||||
// parse terrain damages
|
||||
for (c in payloadBytes["TdMG"]!!.indices step 10) {
|
||||
for (c in 0 until payloadBytes["TdMG"]!!.size step 10) {
|
||||
val bytes = payloadBytes["TdMG"]!!
|
||||
|
||||
val tileAddr = bytes.sliceArray(c..c+5)
|
||||
@@ -167,7 +165,7 @@ internal object ReadLayerDataZip {
|
||||
|
||||
|
||||
// parse wall damages
|
||||
for (c in payloadBytes["WdMG"]!!.indices step 10) {
|
||||
for (c in 0 until payloadBytes["WdMG"]!!.size step 10) {
|
||||
val bytes = payloadBytes["WdMG"]!!
|
||||
|
||||
val tileAddr = bytes.sliceArray(c..c+5)
|
||||
@@ -186,7 +184,7 @@ internal object ReadLayerDataZip {
|
||||
|
||||
spawnPoint.first, spawnPoint.second,
|
||||
|
||||
wallDamages, terrainDamages, fluidTypes, fluidFills, tileNumberToNameMap
|
||||
wallDamages, terrainDamages, fluidTypes, fluidFills
|
||||
)
|
||||
}
|
||||
|
||||
@@ -206,8 +204,7 @@ internal object ReadLayerDataZip {
|
||||
val wallDamages: HashMap<BlockAddress, Float>,
|
||||
val terrainDamages: HashMap<BlockAddress, Float>,
|
||||
val fluidTypes: HashMap<BlockAddress, FluidType>,
|
||||
val fluidFills: HashMap<BlockAddress, Float>,
|
||||
val tileNumberToNameMap: HashMap<Int, ItemID>
|
||||
val fluidFills: HashMap<BlockAddress, Float>
|
||||
)
|
||||
|
||||
internal fun InputStream.readRelative(b: ByteArray, off: Int, len: Int): Int {
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
package net.torvald.terrarum.serialise
|
||||
|
||||
import com.badlogic.gdx.Gdx
|
||||
import net.torvald.random.HQRNG
|
||||
import net.torvald.terrarum.AppLoader
|
||||
import net.torvald.terrarum.Terrarum
|
||||
import net.torvald.terrarum.gameactors.AVKey
|
||||
@@ -9,31 +8,10 @@ import net.torvald.terrarum.gameactors.Actor
|
||||
import net.torvald.terrarum.gameitem.GameItem
|
||||
import net.torvald.terrarum.itemproperties.ItemCodex
|
||||
import net.torvald.terrarum.modulecomputers.virtualcomputer.tvd.*
|
||||
import net.torvald.terrarum.roundInt
|
||||
import net.torvald.terrarum.utils.JsonWriter.getJsonBuilder
|
||||
import net.torvald.util.SortedArrayList
|
||||
import java.io.File
|
||||
import java.nio.charset.Charset
|
||||
import kotlin.math.roundToInt
|
||||
|
||||
internal class RNGPool() {
|
||||
private val RNG = HQRNG()
|
||||
private val used = SortedArrayList<Int>()
|
||||
|
||||
init {
|
||||
for (i in 0 until 32767) {
|
||||
used.add(i)
|
||||
}
|
||||
}
|
||||
|
||||
fun next(): Int {
|
||||
var n = RNG.nextLong().ushr(32).toInt()
|
||||
while (used.contains(n)) {
|
||||
n = RNG.nextLong().ushr(32).toInt()
|
||||
}
|
||||
used.add(n)
|
||||
return n
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Created by minjaesong on 2018-10-03.
|
||||
@@ -42,15 +20,13 @@ object SavegameWriter {
|
||||
|
||||
// TODO create temporary files (worldinfo), create JSON files on RAM, pack those into TEVd as per Savegame container.txt
|
||||
|
||||
private val rngPool = RNGPool()
|
||||
|
||||
private val charset = Charset.forName("UTF-8")
|
||||
|
||||
private lateinit var playerName: String
|
||||
|
||||
operator fun invoke(pnameOverride: String? = null): Boolean {
|
||||
playerName = pnameOverride ?: "${Terrarum.ingame!!.actorGamer!!.actorValue[AVKey.NAME]}"
|
||||
if (playerName.isEmpty()) playerName = "Test subject ${Math.random().times(0x7FFFFFFF).roundToInt()}"
|
||||
if (playerName.isEmpty()) playerName = "Test subject ${Math.random().times(0x7FFFFFFF).roundInt()}"
|
||||
|
||||
try {
|
||||
val diskImage = generateNewDiskImage()
|
||||
@@ -123,16 +99,16 @@ object SavegameWriter {
|
||||
// actors
|
||||
ingame.actorContainerActive.forEach {
|
||||
VDUtil.registerFile(disk, DiskEntry(
|
||||
rngPool.next(), ROOT,
|
||||
it.referenceID.toString(16).toUpperCase().toByteArray(charset),
|
||||
it.referenceID!!, ROOT,
|
||||
it.referenceID!!.toString(16).toUpperCase().toByteArray(charset),
|
||||
creationDate, creationDate,
|
||||
EntryFile(serialiseActor(it))
|
||||
))
|
||||
}
|
||||
ingame.actorContainerInactive.forEach {
|
||||
VDUtil.registerFile(disk, DiskEntry(
|
||||
rngPool.next(), ROOT,
|
||||
it.referenceID.toString(16).toUpperCase().toByteArray(charset),
|
||||
it.referenceID!!, ROOT,
|
||||
it.referenceID!!.toString(16).toUpperCase().toByteArray(charset),
|
||||
creationDate, creationDate,
|
||||
EntryFile(serialiseActor(it))
|
||||
))
|
||||
@@ -141,8 +117,8 @@ object SavegameWriter {
|
||||
// items
|
||||
ItemCodex.dynamicItemDescription.forEach { dynamicID, item ->
|
||||
VDUtil.registerFile(disk, DiskEntry(
|
||||
rngPool.next(), ROOT,
|
||||
dynamicID.toByteArray(charset),
|
||||
item.dynamicID, ROOT,
|
||||
dynamicID.toString(16).toUpperCase().toByteArray(charset),
|
||||
creationDate, creationDate,
|
||||
EntryFile(serialiseItem(item))
|
||||
))
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
package net.torvald.terrarum.serialise
|
||||
|
||||
import net.torvald.terrarum.modulebasegame.worldgenerator.Worldgen
|
||||
import net.torvald.terrarum.modulebasegame.weather.WeatherMixer
|
||||
import net.torvald.terrarum.modulebasegame.worldgenerator.WorldGenerator
|
||||
import net.torvald.terrarum.modulebasegame.worldgenerator.RoguelikeRandomiser
|
||||
import java.nio.charset.Charset
|
||||
|
||||
/**
|
||||
@@ -16,7 +18,7 @@ internal object WriteMeta {
|
||||
|
||||
val BYTE_NULL: Byte = 0
|
||||
|
||||
val terraseed: Long = Worldgen.params.seed
|
||||
val terraseed: Long = WorldGenerator.SEED
|
||||
|
||||
|
||||
/**
|
||||
|
||||
@@ -52,8 +52,8 @@ object WriteWorldInfo {
|
||||
val infile = infileList[filenum - 1]
|
||||
|
||||
infile.forEach {
|
||||
outputStream.write("## from file: ${it.second.nameWithoutExtension()} ##############################\n".toByteArray())
|
||||
val readBytes = it.second.readBytes()
|
||||
outputStream.write("## from file: ${it.nameWithoutExtension()} ##############################\n".toByteArray())
|
||||
val readBytes = it.readBytes()
|
||||
outputStream.write(readBytes)
|
||||
outputStream.write("\n".toByteArray())
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user