diff --git a/core/assets-raw/sprites/enemies/fortressenemy-t1.png b/core/assets-raw/sprites/enemies/fortressenemy-t1.png new file mode 100644 index 0000000000..08af9a95b3 Binary files /dev/null and b/core/assets-raw/sprites/enemies/fortressenemy-t1.png differ diff --git a/core/assets-raw/sprites/enemies/fortressenemy-t2.png b/core/assets-raw/sprites/enemies/fortressenemy-t2.png new file mode 100644 index 0000000000..07eec2cd31 Binary files /dev/null and b/core/assets-raw/sprites/enemies/fortressenemy-t2.png differ diff --git a/core/assets-raw/sprites/enemies/fortressenemy-t3.png b/core/assets-raw/sprites/enemies/fortressenemy-t3.png new file mode 100644 index 0000000000..7beb99e5f7 Binary files /dev/null and b/core/assets-raw/sprites/enemies/fortressenemy-t3.png differ diff --git a/core/assets/sprites/sprites.atlas b/core/assets/sprites/sprites.atlas index 6b1f113a62..adb28767e7 100644 --- a/core/assets/sprites/sprites.atlas +++ b/core/assets/sprites/sprites.atlas @@ -13,77 +13,77 @@ backgrounds/background index: -1 blank rotate: false - xy: 473, 386 + xy: 308, 147 size: 1, 1 orig: 1, 1 offset: 0, 0 index: -1 blocks/blackrock1 rotate: false - xy: 230, 67 + xy: 415, 313 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackrockshadow1 rotate: false - xy: 240, 67 + xy: 450, 480 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstone1 rotate: false - xy: 450, 480 + xy: 348, 231 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstone2 rotate: false - xy: 343, 199 + xy: 450, 470 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstone3 rotate: false - xy: 450, 470 + xy: 348, 221 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstoneblock1 rotate: false - xy: 333, 197 + xy: 374, 222 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstoneblock2 rotate: false - xy: 343, 189 + xy: 374, 212 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstoneblock3 rotate: false - xy: 333, 187 + xy: 325, 197 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/blackstoneedge rotate: false - xy: 499, 499 + xy: 206, 1 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/block rotate: false - xy: 443, 303 + xy: 337, 211 size: 8, 8 orig: 8, 8 offset: 0, 0 @@ -111,105 +111,105 @@ blocks/chainturret index: -1 blocks/chainturret-icon rotate: false - xy: 411, 323 + xy: 230, 67 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/coal1 rotate: false - xy: 443, 283 + xy: 327, 168 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/coal2 rotate: false - xy: 439, 273 + xy: 327, 158 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/coal3 rotate: false - xy: 439, 263 + xy: 327, 148 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/coaldrill rotate: false - xy: 439, 253 + xy: 431, 311 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/coalgenerator rotate: false - xy: 232, 11 + xy: 431, 301 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/coalpurifier rotate: false - xy: 232, 1 + xy: 441, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/combustiongenerator rotate: false - xy: 242, 13 + xy: 451, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/compositewall rotate: false - xy: 242, 3 + xy: 461, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/conduit rotate: false - xy: 469, 355 + xy: 471, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/conduitbottom rotate: false - xy: 449, 273 + xy: 481, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/conduitliquid rotate: false - xy: 449, 263 + xy: 441, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/conduittop rotate: false - xy: 449, 253 + xy: 451, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/conveyor rotate: false - xy: 476, 415 + xy: 461, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/conveyormove rotate: false - xy: 476, 405 + xy: 471, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 @@ -223,294 +223,294 @@ blocks/core index: -1 blocks/cross rotate: false - xy: 476, 395 + xy: 481, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/crucible rotate: false - xy: 476, 385 + xy: 431, 291 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/deepwater rotate: false - xy: 473, 375 + xy: 441, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/dirt1 rotate: false - xy: 473, 365 + xy: 451, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/dirt2 rotate: false - xy: 479, 355 + xy: 461, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/dirt3 rotate: false - xy: 367, 174 + xy: 471, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/dirtblock rotate: false - xy: 483, 375 + xy: 481, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/dirtedge rotate: false - xy: 499, 485 + xy: 220, 1 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/doubleturret rotate: false - xy: 456, 425 + xy: 308, 132 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/duriumwall rotate: false - xy: 483, 365 + xy: 427, 281 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/duriumwall-large rotate: false - xy: 228, 113 + xy: 247, 116 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 blocks/duriumwall-large-icon rotate: false - xy: 489, 355 + xy: 427, 271 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/flameturret rotate: false - xy: 452, 413 + xy: 320, 132 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/fluxpump rotate: false - xy: 415, 198 + xy: 437, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grass1 rotate: false - xy: 427, 217 + xy: 447, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grass2 rotate: false - xy: 425, 207 + xy: 437, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grass3 rotate: false - xy: 425, 197 + xy: 457, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassblock-edge-0 rotate: false - xy: 413, 178 + xy: 457, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassblock-edge-1 rotate: false - xy: 423, 177 + xy: 477, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassblock-edge-2 rotate: false - xy: 443, 341 + xy: 467, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassblock-edge-3 rotate: false - xy: 453, 343 + xy: 477, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassblock1 rotate: false - xy: 415, 188 + xy: 447, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassblock2 rotate: false - xy: 425, 187 + xy: 467, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/grassedge rotate: false - xy: 353, 181 + xy: 411, 247 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/iron1 rotate: false - xy: 503, 431 + xy: 355, 186 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/iron2 rotate: false - xy: 503, 421 + xy: 355, 176 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/iron3 rotate: false - xy: 503, 411 + xy: 487, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/irondrill rotate: false - xy: 503, 401 + xy: 487, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/ironwall rotate: false - xy: 503, 391 + xy: 264, 46 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/junction rotate: false - xy: 503, 381 + xy: 262, 36 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/laserturret rotate: false - xy: 317, 131 + xy: 459, 331 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/lava rotate: false - xy: 503, 371 + xy: 472, 439 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/lavaedge rotate: false - xy: 399, 179 + xy: 417, 233 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/lavasmelter rotate: false - xy: 503, 361 + xy: 472, 429 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/liquiditemjunction rotate: false - xy: 503, 351 + xy: 472, 419 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/liquidjunction rotate: false - xy: 503, 341 + xy: 490, 459 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/liquidrouter rotate: false - xy: 493, 443 + xy: 500, 459 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/machineturret rotate: false - xy: 329, 131 + xy: 457, 319 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/megarepairturret rotate: false - xy: 341, 131 + xy: 473, 355 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/mortarturret rotate: false - xy: 230, 21 + xy: 473, 343 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/mossblock rotate: false - xy: 493, 423 + xy: 485, 449 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/mossstone rotate: false - xy: 493, 423 + xy: 485, 449 size: 8, 8 orig: 8, 8 offset: 0, 0 @@ -524,385 +524,385 @@ blocks/nuclearreactor index: -1 blocks/nuclearreactor-icon rotate: false - xy: 493, 403 + xy: 495, 449 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/nuclearreactor-small rotate: false - xy: 247, 132 + xy: 265, 118 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 blocks/oil rotate: false - xy: 493, 393 + xy: 482, 429 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/oiledge rotate: false - xy: 460, 465 + xy: 417, 219 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/oilrefinery rotate: false - xy: 493, 383 + xy: 492, 439 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/omnidrill rotate: false - xy: 493, 373 + xy: 482, 419 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/plasmaturret rotate: false - xy: 242, 23 + xy: 471, 331 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/powerbooster rotate: false - xy: 301, 124 + xy: 492, 429 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/poweredconveyor rotate: false - xy: 439, 243 + xy: 492, 419 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/poweredconveyormove rotate: false - xy: 449, 243 + xy: 480, 409 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/powerlaser rotate: false - xy: 433, 233 + xy: 480, 399 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/powerlaserrouter rotate: false - xy: 443, 233 + xy: 490, 409 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/pulseconduit rotate: false - xy: 453, 233 + xy: 480, 389 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/pulseconduitbottom rotate: false - xy: 437, 223 + xy: 480, 379 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/pulseconduittop rotate: false - xy: 447, 223 + xy: 490, 399 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/pump rotate: false - xy: 437, 213 + xy: 490, 389 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/repairturret rotate: false - xy: 464, 413 + xy: 469, 319 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/rock1 rotate: false - xy: 435, 203 + xy: 489, 369 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/rock2 rotate: false - xy: 435, 193 + xy: 367, 202 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/rockshadow1 rotate: false - xy: 445, 203 + xy: 377, 202 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/rockshadow2 rotate: false - xy: 445, 193 + xy: 387, 203 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/router rotate: false - xy: 457, 223 + xy: 397, 203 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/rtgenerator rotate: false - xy: 457, 213 + xy: 367, 192 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/shadow rotate: false - xy: 464, 401 + xy: 477, 367 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/shieldgenerator rotate: false - xy: 455, 193 + xy: 387, 193 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/shotgunturret rotate: false - xy: 464, 389 + xy: 485, 355 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/shrub rotate: false - xy: 455, 183 + xy: 375, 182 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/shrubshadow rotate: false - xy: 433, 173 + xy: 365, 172 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/smelter rotate: false - xy: 443, 173 + xy: 375, 172 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/sniperturret rotate: false - xy: 461, 377 + xy: 485, 343 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/sorter rotate: false - xy: 453, 173 + xy: 502, 439 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/steelconveyor rotate: false - xy: 252, 13 + xy: 502, 429 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/steelconveyormove rotate: false - xy: 252, 3 + xy: 502, 419 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/steelwall rotate: false - xy: 343, 165 + xy: 500, 409 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/steelwall-large rotate: false - xy: 265, 132 + xy: 290, 132 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 blocks/steelwall-large-icon rotate: false - xy: 353, 171 + xy: 500, 399 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stone rotate: false - xy: 456, 451 + xy: 431, 233 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/stone1 rotate: false - xy: 353, 161 + xy: 500, 389 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stone2 rotate: false - xy: 353, 151 + xy: 500, 379 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stone3 rotate: false - xy: 353, 141 + xy: 499, 369 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock-edge-0 rotate: false - xy: 363, 144 + xy: 495, 329 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock-edge-1 rotate: false - xy: 363, 134 + xy: 493, 319 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock-edge-2 rotate: false - xy: 373, 164 + xy: 503, 319 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock-edge-3 rotate: false - xy: 373, 154 + xy: 491, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock-smooth1 rotate: false - xy: 373, 144 + xy: 491, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock1 rotate: false - xy: 353, 131 + xy: 497, 359 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock2 rotate: false - xy: 363, 164 + xy: 497, 349 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneblock3 rotate: false - xy: 363, 154 + xy: 497, 339 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stonedrill rotate: false - xy: 373, 134 + xy: 491, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stoneedge rotate: false - xy: 456, 437 + xy: 431, 219 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/stoneformer rotate: false - xy: 383, 167 + xy: 501, 309 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/stonewall rotate: false - xy: 383, 157 + xy: 501, 299 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/teleporter rotate: false - xy: 383, 147 + xy: 501, 289 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/teleporter-top rotate: false - xy: 383, 137 + xy: 497, 279 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/thermalgenerator rotate: false - xy: 393, 167 + xy: 497, 269 size: 8, 8 orig: 8, 8 offset: 0, 0 @@ -916,147 +916,147 @@ blocks/titancannon index: -1 blocks/titancannon-icon rotate: false - xy: 461, 365 + xy: 483, 331 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/titanium1 rotate: false - xy: 393, 157 + xy: 265, 108 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titanium2 rotate: false - xy: 393, 147 + xy: 264, 98 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titanium3 rotate: false - xy: 393, 137 + xy: 264, 88 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titaniumdrill rotate: false - xy: 403, 169 + xy: 274, 46 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titaniumpurifier rotate: false - xy: 413, 168 + xy: 272, 36 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titaniumshieldwall rotate: false - xy: 423, 167 + xy: 270, 26 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titaniumwall rotate: false - xy: 403, 159 + xy: 439, 259 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/titaniumwall-large rotate: false - xy: 317, 207 + xy: 230, 79 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 blocks/titaniumwall-large-icon rotate: false - xy: 403, 149 + xy: 449, 259 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/turret rotate: false - xy: 457, 353 + xy: 481, 319 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 blocks/uranium1 rotate: false - xy: 413, 148 + xy: 449, 249 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/uranium2 rotate: false - xy: 423, 157 + xy: 469, 259 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/uranium3 rotate: false - xy: 433, 163 + xy: 459, 249 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/uraniumdrill rotate: false - xy: 443, 163 + xy: 479, 259 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/water rotate: false - xy: 453, 163 + xy: 469, 249 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 blocks/wateredge rotate: false - xy: 470, 451 + xy: 250, 53 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 blocks/waveturret rotate: false - xy: 468, 425 + xy: 325, 207 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 bullet rotate: false - xy: 443, 293 + xy: 347, 211 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 chainbullet rotate: false - xy: 311, 150 + xy: 325, 178 size: 8, 7 orig: 8, 7 offset: 0, 0 index: -1 circle rotate: false - xy: 228, 131 + xy: 228, 115 size: 17, 17 orig: 17, 17 offset: 0, 0 @@ -1070,322 +1070,343 @@ circle2 index: -1 enemies/blastenemy-t1 rotate: false - xy: 342, 225 + xy: 248, 100 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/blastenemy-t2 rotate: false - xy: 317, 191 + xy: 248, 84 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/blastenemy-t3 rotate: false - xy: 335, 209 + xy: 385, 225 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/empenemy-t1 rotate: false - xy: 317, 175 + xy: 401, 225 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/empenemy-t2 rotate: false - xy: 433, 371 + xy: 413, 353 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/empenemy-t3 rotate: false - xy: 301, 134 + xy: 429, 353 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/enemy-t1 rotate: false - xy: 311, 159 + xy: 411, 337 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/targetenemy-t1 rotate: false - xy: 311, 159 + xy: 411, 337 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/enemy-t2 rotate: false - xy: 499, 471 + xy: 411, 323 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 enemies/enemy-t3 rotate: false - xy: 353, 195 + xy: 476, 465 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 enemies/fastenemy-t1 rotate: false - xy: 385, 225 + xy: 427, 337 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/fastenemy-t2 rotate: false - xy: 401, 225 + xy: 425, 321 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/fastenemy-t3 rotate: false - xy: 351, 209 + xy: 234, 51 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/flamerenemy-t1 rotate: false - xy: 367, 216 + xy: 234, 35 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/flamerenemy-t2 rotate: false - xy: 367, 200 + xy: 283, 116 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/flamerenemy-t3 rotate: false - xy: 383, 209 + xy: 299, 116 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 +enemies/fortressenemy-t1 + rotate: false + xy: 491, 491 + size: 20, 20 + orig: 20, 20 + offset: 0, 0 + index: -1 +enemies/fortressenemy-t2 + rotate: false + xy: 491, 469 + size: 20, 20 + orig: 20, 20 + offset: 0, 0 + index: -1 +enemies/fortressenemy-t3 + rotate: false + xy: 306, 219 + size: 20, 20 + orig: 20, 20 + offset: 0, 0 + index: -1 enemies/healerenemy-t1 rotate: false - xy: 399, 209 + xy: 415, 297 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/healerenemy-t2 rotate: false - xy: 383, 193 + xy: 311, 160 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/healerenemy-t3 rotate: false - xy: 399, 193 + xy: 311, 144 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/mortarenemy-t1 rotate: false - xy: 429, 351 + xy: 449, 367 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/mortarenemy-t2 rotate: false - xy: 417, 227 + xy: 445, 351 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/mortarenemy-t3 rotate: false - xy: 327, 159 + xy: 443, 335 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/rapidenemy-t1 rotate: false - xy: 321, 143 + xy: 441, 319 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/rapidenemy-t2 rotate: false - xy: 234, 51 + xy: 358, 216 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/rapidenemy-t3 rotate: false - xy: 234, 35 + xy: 230, 17 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/tankenemy-t1 rotate: false - xy: 337, 143 + xy: 234, 1 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/tankenemy-t2 rotate: false - xy: 367, 184 + xy: 411, 277 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/tankenemy-t3 rotate: false - xy: 383, 177 + xy: 411, 261 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 enemies/titanenemy-t1 rotate: false - xy: 283, 132 + xy: 413, 369 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 enemies/titanenemy-t2 rotate: false - xy: 230, 95 + xy: 431, 369 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 enemies/titanenemy-t3 rotate: false - xy: 230, 77 + xy: 230, 97 size: 16, 16 orig: 16, 16 offset: 0, 0 index: -1 enemyarrow rotate: false - xy: 417, 218 + xy: 337, 202 size: 8, 7 orig: 8, 7 offset: 0, 0 index: -1 icon-coal rotate: false - xy: 463, 343 + xy: 347, 201 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 icon-dirium rotate: false - xy: 473, 345 + xy: 357, 206 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 icon-iron rotate: false - xy: 483, 345 + xy: 335, 192 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 icon-steel rotate: false - xy: 493, 345 + xy: 335, 182 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 icon-stone rotate: false - xy: 503, 461 + xy: 345, 191 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 icon-titanium rotate: false - xy: 503, 451 + xy: 345, 181 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 icon-uranium rotate: false - xy: 503, 441 + xy: 357, 196 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 laser rotate: false - xy: 488, 465 + xy: 472, 449 size: 1, 12 orig: 1, 12 offset: 0, 0 index: -1 laserend rotate: false - xy: 413, 367 + xy: 328, 221 size: 18, 18 orig: 18, 18 offset: 0, 0 index: -1 mechs/player rotate: false - xy: 474, 465 + xy: 425, 247 size: 12, 12 orig: 12, 12 offset: 0, 0 index: -1 shell rotate: false - xy: 455, 203 + xy: 377, 192 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 shot rotate: false - xy: 435, 183 + xy: 397, 193 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 shot-long rotate: false - xy: 445, 183 + xy: 365, 182 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 titanshell rotate: false - xy: 413, 158 + xy: 439, 249 size: 8, 8 orig: 8, 8 offset: 0, 0 @@ -1477,42 +1498,42 @@ ui/check-over index: -1 ui/clear rotate: false - xy: 423, 323 + xy: 242, 67 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/cursor rotate: false - xy: 377, 178 + xy: 411, 241 size: 4, 4 orig: 4, 4 offset: 0, 0 index: -1 ui/icon-arrow-left rotate: false - xy: 470, 439 + xy: 250, 41 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-arrow-right rotate: false - xy: 452, 401 + xy: 250, 29 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-cancel rotate: false - xy: 413, 351 + xy: 254, 68 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-check rotate: false - xy: 411, 335 + xy: 315, 116 size: 14, 14 orig: 14, 14 offset: 0, 0 @@ -1540,133 +1561,133 @@ ui/icon-close-over index: -1 ui/icon-crafting rotate: false - xy: 452, 389 + xy: 246, 17 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-cursor rotate: false - xy: 449, 377 + xy: 250, 5 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-defense rotate: false - xy: 333, 175 + xy: 258, 17 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-distribution rotate: false - xy: 435, 323 + xy: 262, 5 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-info rotate: false - xy: 431, 311 + xy: 264, 56 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-load rotate: false - xy: 415, 307 + xy: 460, 463 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-menu rotate: false - xy: 431, 299 + xy: 384, 213 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-pause rotate: false - xy: 431, 287 + xy: 396, 213 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-play rotate: false - xy: 427, 275 + xy: 468, 403 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-play-2 rotate: false - xy: 415, 291 + xy: 456, 447 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-power rotate: false - xy: 427, 263 + xy: 468, 391 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-production rotate: false - xy: 427, 251 + xy: 468, 379 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-rotate rotate: false - xy: 411, 275 + xy: 456, 431 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-rotate-arrow rotate: false - xy: 411, 259 + xy: 456, 415 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-settings rotate: false - xy: 484, 453 + xy: 465, 367 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-tools rotate: false - xy: 411, 243 + xy: 452, 399 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-touch rotate: false - xy: 449, 365 + xy: 461, 355 size: 10, 10 orig: 10, 10 offset: 0, 0 index: -1 ui/icon-tutorial rotate: false - xy: 427, 335 + xy: 452, 383 size: 14, 14 orig: 14, 14 offset: 0, 0 index: -1 ui/icon-weapon rotate: false - xy: 445, 353 + xy: 461, 343 size: 10, 10 orig: 10, 10 offset: 0, 0 @@ -1703,7 +1724,7 @@ ui/pane-button index: -1 ui/scroll rotate: false - xy: 306, 225 + xy: 228, 134 size: 34, 6 split: 4, 4, 2, 2 orig: 34, 6 @@ -1720,7 +1741,7 @@ ui/scroll-horizontal index: -1 ui/scroll-knob-horizontal rotate: false - xy: 491, 477 + xy: 317, 183 size: 6, 34 split: 2, 2, 0, 34 pad: 0, 5, 13, 12 @@ -1729,7 +1750,7 @@ ui/scroll-knob-horizontal index: -1 ui/scroll-knob-vertical rotate: false - xy: 306, 233 + xy: 228, 142 size: 34, 6 split: 12, 12, 2, 2 orig: 34, 6 @@ -1737,21 +1758,21 @@ ui/scroll-knob-vertical index: -1 ui/selection rotate: false - xy: 383, 391 + xy: 308, 144 size: 1, 1 orig: 1, 1 offset: 0, 0 index: -1 ui/separator rotate: false - xy: 194, 35 + xy: 465, 380 size: 1, 1 orig: 1, 1 offset: 0, 0 index: -1 ui/slider rotate: false - xy: 383, 394 + xy: 452, 415 size: 1, 8 orig: 1, 8 offset: 0, 0 @@ -1786,7 +1807,7 @@ ui/slider-vertical index: -1 ui/text-exit rotate: false - xy: 206, 1 + xy: 264, 136 size: 24, 12 orig: 24, 12 offset: 0, 0 @@ -1881,42 +1902,42 @@ ui/window-empty index: -1 weapons/blaster rotate: false - xy: 443, 313 + xy: 325, 187 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 weapons/flamer rotate: false - xy: 415, 208 + xy: 427, 261 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 weapons/mortar rotate: false - xy: 493, 433 + xy: 475, 449 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 weapons/multigun rotate: false - xy: 493, 413 + xy: 482, 439 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 weapons/railgun rotate: false - xy: 447, 213 + xy: 490, 379 size: 8, 8 orig: 8, 8 offset: 0, 0 index: -1 weapons/triblaster rotate: false - xy: 403, 139 + xy: 459, 259 size: 8, 8 orig: 8, 8 offset: 0, 0 diff --git a/core/assets/sprites/sprites.png b/core/assets/sprites/sprites.png index 19b547ce51..4c9e7658ba 100644 Binary files a/core/assets/sprites/sprites.png and b/core/assets/sprites/sprites.png differ diff --git a/core/src/io/anuke/mindustry/Mindustry.java b/core/src/io/anuke/mindustry/Mindustry.java index 50a17523c1..def6b2be5d 100644 --- a/core/src/io/anuke/mindustry/Mindustry.java +++ b/core/src/io/anuke/mindustry/Mindustry.java @@ -31,6 +31,7 @@ public class Mindustry extends ModuleCore { } }; + //always initialize blocks in this order, otherwise there are ID errors public Block[] blockClasses = { Blocks.air, diff --git a/core/src/io/anuke/mindustry/ai/Pathfind.java b/core/src/io/anuke/mindustry/ai/Pathfind.java index 3f2b34cdaf..e239913791 100644 --- a/core/src/io/anuke/mindustry/ai/Pathfind.java +++ b/core/src/io/anuke/mindustry/ai/Pathfind.java @@ -82,7 +82,7 @@ public class Pathfind{ for(SpawnPoint point : Vars.control.getSpawnPoints()){ if(!point.request.pathFound){ - if(point.finder.search(point.request, ms*2)){ + if(point.finder.search(point.request, ms)){ smoother.smoothPath(point.path); point.pathTiles = point.path.nodes.toArray(Tile.class); } diff --git a/core/src/io/anuke/mindustry/core/Control.java b/core/src/io/anuke/mindustry/core/Control.java index 2495cd0f09..c93d7add2d 100644 --- a/core/src/io/anuke/mindustry/core/Control.java +++ b/core/src/io/anuke/mindustry/core/Control.java @@ -36,7 +36,7 @@ import io.anuke.ucore.util.Profiler; public class Control extends Module{ int targetscale = baseCameraScale; - public Tutorial tutorial = new Tutorial(); + Tutorial tutorial = new Tutorial(); boolean hiscore = false; final Array weapons = new Array<>(); @@ -51,6 +51,7 @@ public class Control extends Module{ float wavetime; float extrawavetime; int enemies = 0; + GameMode mode = GameMode.waves; Tile core; Array spawnpoints = new Array<>(); @@ -162,7 +163,7 @@ public class Control extends Module{ public void reset(){ weapons.clear(); - Vars.renderer.clearTiles(); + renderer.clearTiles(); weapons.add(Weapon.blaster); player.weapon = weapons.first(); @@ -187,7 +188,7 @@ public class Control extends Module{ } public void play(){ - Vars.renderer.clearTiles(); + renderer.clearTiles(); player.x = core.worldx(); player.y = core.worldy() - Vars.tilesize*2 - ((int)(Gdx.graphics.getWidth() / (float)Core.cameraScale * 2) % 2 == 0 ? 0.5f : 0); @@ -232,6 +233,14 @@ public class Control extends Module{ }); } + public GameMode getMode(){ + return mode; + } + + public void setMode(GameMode mode){ + this.mode = mode; + } + public boolean hasWeapon(Weapon weapon){ return weapons.contains(weapon, true); } @@ -443,7 +452,7 @@ public class Control extends Module{ if(Inputs.keyDown(Keys.SHIFT_LEFT)){ new HealerEnemy(0).set(player.x, player.y).add(); }else{ - new TitanEnemy(0).set(player.x, player.y).add(); + new FortressEnemy(0).set(player.x, player.y).add(); } } } @@ -479,17 +488,19 @@ public class Control extends Module{ } } - if(!tutorial.active()){ + if(tutorial.active()){ + tutorial.update(); + } + + if(!tutorial.active() && mode != GameMode.sandbox){ extrawavetime -= delta(); if(enemies <= 0){ wavetime -= delta(); } - }else{ - tutorial.update(); } - if(wavetime <= 0 || (debug && Inputs.keyUp(Keys.F)) || extrawavetime <= 0){ + if(wavetime <= 0){ runWave(); } diff --git a/core/src/io/anuke/mindustry/entities/BulletType.java b/core/src/io/anuke/mindustry/entities/BulletType.java index 0db38cca5a..12de2f69d5 100644 --- a/core/src/io/anuke/mindustry/entities/BulletType.java +++ b/core/src/io/anuke/mindustry/entities/BulletType.java @@ -20,6 +20,7 @@ public abstract class BulletType extends BaseBulletType{ static Color lightRed = Hue.mix(Color.WHITE, Color.FIREBRICK, 0.1f); static Color lightOrange = Color.valueOf("f68021"); static Color whiteOrange = Hue.mix(lightOrange, Color.WHITE, 0.6f); + static Color whiteYellow = Hue.mix(Color.YELLOW, Color.WHITE, 0.6f); public static final BulletType @@ -128,7 +129,7 @@ public abstract class BulletType extends BaseBulletType{ Effects.effect(Fx.shellsmoke, b); Effects.effect(Fx.shellexplosion, b); - DamageArea.damage(b.owner instanceof Enemy, b.x, b.y, 25f, (int)(damage * 2f/3f)); + DamageArea.damage(!(b.owner instanceof Enemy), b.x, b.y, 25f, (int)(damage * 2f/3f)); } }, titanshell = new BulletType(1.8f, 60){ @@ -162,6 +163,37 @@ public abstract class BulletType extends BaseBulletType{ DamageArea.damage(!(b.owner instanceof Enemy), b.x, b.y, 25f, (int)(damage * 2f/3f)); } }, + yellowshell = new BulletType(1.2f, 20){ + { + lifetime = 60f; + hitsize = 11f; + } + + public void draw(Bullet b){ + Draw.color(whiteYellow); + Draw.rect("titanshell", b.x, b.y, b.angle()); + Draw.reset(); + } + + public void update(Bullet b){ + if(Timers.get(b, "smoke", 4)){ + Effects.effect(Fx.smoke, b.x + Mathf.range(2), b.y + Mathf.range(2)); + } + } + + public void despawned(Bullet b){ + removed(b); + } + + public void removed(Bullet b){ + Effects.shake(3f, 3f, b); + + Effects.effect(Fx.shellsmoke, b); + Effects.effect(Fx.shockwaveSmall, b); + + DamageArea.damage(!(b.owner instanceof Enemy), b.x, b.y, 25f, (int)(damage * 2f/3f)); + } + }, blast = new BulletType(1.1f, 80){ { lifetime = 0f; diff --git a/core/src/io/anuke/mindustry/entities/effect/DamageArea.java b/core/src/io/anuke/mindustry/entities/effect/DamageArea.java index 0a270326c0..51f8415b2a 100644 --- a/core/src/io/anuke/mindustry/entities/effect/DamageArea.java +++ b/core/src/io/anuke/mindustry/entities/effect/DamageArea.java @@ -14,7 +14,7 @@ public class DamageArea{ public static void damage(boolean enemies, float x, float y, float radius, int damage){ if(enemies){ - Entities.getNearby(x, y, radius*2, entity->{ + Entities.getNearby(Entities.getGroup(Enemy.class), x, y, radius*2, entity->{ if(entity instanceof Enemy){ Enemy enemy = (Enemy)entity; if(enemy.distanceTo(x, y) > radius){ diff --git a/core/src/io/anuke/mindustry/entities/effect/Fx.java b/core/src/io/anuke/mindustry/entities/effect/Fx.java index f305b020a0..feec4f2403 100644 --- a/core/src/io/anuke/mindustry/entities/effect/Fx.java +++ b/core/src/io/anuke/mindustry/entities/effect/Fx.java @@ -13,6 +13,7 @@ public class Fx{ static Color lightRed = Hue.mix(Color.WHITE, Color.FIREBRICK, 0.1f); static Color lightOrange = Color.valueOf("f68021"); static Color whiteOrange = Hue.mix(lightOrange, Color.WHITE, 0.6f); + static Color whiteYellow = Hue.mix(Color.YELLOW, Color.WHITE, 0.6f); public static final Effect @@ -34,6 +35,28 @@ public class Fx{ Draw.reset(); }), + mortarshot = new Effect(10f, e -> { + Draw.color(Color.WHITE, Color.DARK_GRAY, e.ifract()); + Draw.thick(e.fract()*6f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*10f); + Draw.thick(e.fract()*5f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*14f); + Draw.thick(e.fract()*1f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*16f); + Draw.reset(); + }), + + railshot = new Effect(9f, e -> { + Draw.color(Color.WHITE, Color.DARK_GRAY, e.ifract()); + Draw.thick(e.fract()*5f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*8f); + Draw.thick(e.fract()*4f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*12f); + Draw.thick(e.fract()*1f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*14f); + Draw.reset(); + }), + titanshot = new Effect(12f, e -> { Draw.color(Color.WHITE, lightOrange, e.ifract()); Draw.thick(e.fract()*7f); @@ -45,6 +68,17 @@ public class Fx{ Draw.reset(); }), + largeCannonShot = new Effect(11f, e -> { + Draw.color(Color.WHITE, whiteYellow, e.ifract()); + Draw.thick(e.fract()*6f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*12f); + Draw.thick(e.fract()*3f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*16f); + Draw.thick(e.fract()*1f); + Draw.lineAngle(e.x, e.y, e.rotation, e.fract()*18f); + Draw.reset(); + }), + shockwave = new Effect(10f, e -> { Draw.color(Color.WHITE, Color.LIGHT_GRAY, e.ifract()); Draw.thick(e.fract()*2f + 0.2f); diff --git a/core/src/io/anuke/mindustry/entities/enemies/Enemy.java b/core/src/io/anuke/mindustry/entities/enemies/Enemy.java index e510681f7a..91ba5b1e25 100644 --- a/core/src/io/anuke/mindustry/entities/enemies/Enemy.java +++ b/core/src/io/anuke/mindustry/entities/enemies/Enemy.java @@ -11,8 +11,10 @@ import io.anuke.mindustry.entities.Player; import io.anuke.mindustry.entities.effect.Fx; import io.anuke.mindustry.entities.effect.Shaders; import io.anuke.mindustry.world.Tile; +import io.anuke.ucore.UCore; import io.anuke.ucore.core.*; import io.anuke.ucore.entities.*; +import io.anuke.ucore.util.Angles; import io.anuke.ucore.util.Mathf; import io.anuke.ucore.util.Tmp; @@ -24,18 +26,21 @@ public class Enemy extends DestructibleEntity{ protected float reload = 32; protected float range = 60; protected float length = 4; - protected float rotatespeed = 7f; + protected float rotatespeed = 0.1f; protected float turretrotatespeed = 0.2f; protected boolean alwaysRotate = false; protected BulletType bullet = BulletType.small; protected String shootsound = "enemyshoot"; protected int damage; + protected Enemy spawner; + protected int spawned = 0; + protected float angle; + protected boolean targetCore = false; public int spawn; public int node = -1; public Tile[] path; - public Vector2 direction = new Vector2(); public float xvelocity, yvelocity; public Entity target; public int tier = 1; @@ -63,7 +68,7 @@ public class Enemy extends DestructibleEntity{ if(nearCore){ vec = Tmp.v2.setZero(); - target = core.entity; + if(targetCore) target = core.entity; }else{ vec = Vars.world.pathfinder().find(this); vec.sub(x, y).setLength(speed); @@ -94,7 +99,6 @@ public class Enemy extends DestructibleEntity{ move(vec.x * Timers.delta(), vec.y * Timers.delta()); - updateTargeting(nearCore); } @@ -107,6 +111,10 @@ public class Enemy extends DestructibleEntity{ target = Entities.getClosest(Entities.defaultGroup(), x, y, range, e -> e instanceof Player); } } + + if(target instanceof Enemy){ + UCore.log(target); + } if(target != null && bullet != null){ updateShooting(); @@ -125,8 +133,8 @@ public class Enemy extends DestructibleEntity{ } void shoot(BulletType bullet, float rotation){ - vector.set(length, 0).rotate(direction.angle() + rotation); - Bullet out = new Bullet(bullet, this, x + vector.x, y + vector.y, direction.angle() + rotation).add(); + Angles.translation(angle + rotation, length); + Bullet out = new Bullet(bullet, this, x + Angles.x(), y + Angles.y(), this.angle + rotation).add(); out.damage = (int) (damage * Vars.multiplier); } @@ -195,6 +203,9 @@ public class Enemy extends DestructibleEntity{ public void removed(){ if(!dead){ Vars.control.enemyDeath(); + if(spawner != null){ + spawner.spawned --; + } } } @@ -208,11 +219,9 @@ public class Enemy extends DestructibleEntity{ yvelocity = (y - lasty) / Timers.delta(); if(target == null || alwaysRotate){ - direction.add(xvelocity * Timers.delta() / 3f, yvelocity * Timers.delta() / 3f); - direction.limit(speed * rotatespeed); + angle = Mathf.slerp(angle, 180f+Mathf.atan2(xvelocity, yvelocity), rotatespeed * Timers.delta()); }else{ - float angle = angleTo(target); - direction.lerp(vector.set(1f, 0f).rotate(angle), turretrotatespeed * Timers.delta()); + angle = Mathf.slerp(angle, angleTo(target), turretrotatespeed * Timers.delta()); } } @@ -226,7 +235,7 @@ public class Enemy extends DestructibleEntity{ Shaders.outline.apply(); Draw.color(); - Draw.rect(region, x, y, direction.angle() - 90); + Draw.rect(region, x, y, this.angle - 90); Graphics.flush(); diff --git a/core/src/io/anuke/mindustry/entities/enemies/FortressEnemy.java b/core/src/io/anuke/mindustry/entities/enemies/FortressEnemy.java new file mode 100644 index 0000000000..9a387c5c22 --- /dev/null +++ b/core/src/io/anuke/mindustry/entities/enemies/FortressEnemy.java @@ -0,0 +1,62 @@ +package io.anuke.mindustry.entities.enemies; + +import io.anuke.mindustry.Vars; +import io.anuke.mindustry.entities.BulletType; +import io.anuke.mindustry.entities.effect.Fx; +import io.anuke.ucore.core.Effects; +import io.anuke.ucore.core.Timers; +import io.anuke.ucore.util.Angles; + +public class FortressEnemy extends Enemy{ + static int maxSpawn = 6; + + float spawnTime = 240; + boolean deployed; + + public FortressEnemy(int spawn) { + super(spawn); + + speed = 0.1f; + reload = 90; + maxhealth = 700; + range = 70f; + bullet = BulletType.yellowshell; + hitbox.setSize(9f); + turretrotatespeed = rotatespeed = 0.08f; + length = 7f; + + heal(); + } + + @Override + public void move(){ + super.move(); + + if(deployed){ + + if(Timers.get(this, "spawn", spawnTime) && spawned < maxSpawn){ + Angles.translation(angle, 20f); + + FastEnemy enemy = new FastEnemy(spawn); + enemy.tier = this.tier; + enemy.spawner = this; + enemy.set(x + Angles.x(), y + Angles.y()); + Effects.effect(Fx.spawn, enemy); + enemy.add(); + spawned ++; + } + }else if(distanceTo(Vars.control.getCore().worldx(), + Vars.control.getCore().worldy()) <= 120f){ + deployed = true; + speed = 0.001f; + } + } + + @Override + public void shoot(BulletType type){ + super.shoot(bullet); + Effects.effect(Fx.largeCannonShot, x + Angles.x(), y + Angles.y(), angle); + Effects.shake(3f, 3f, this); + } + +} diff --git a/core/src/io/anuke/mindustry/entities/enemies/HealerEnemy.java b/core/src/io/anuke/mindustry/entities/enemies/HealerEnemy.java index 7f46b9c607..ae3ab9675c 100644 --- a/core/src/io/anuke/mindustry/entities/enemies/HealerEnemy.java +++ b/core/src/io/anuke/mindustry/entities/enemies/HealerEnemy.java @@ -23,6 +23,7 @@ public class HealerEnemy extends Enemy{ bullet = BulletType.shot; range = 30f; alwaysRotate = false; + targetCore = false; heal(); } diff --git a/core/src/io/anuke/mindustry/entities/enemies/TankEnemy.java b/core/src/io/anuke/mindustry/entities/enemies/TankEnemy.java index 0558d950c5..153e79471c 100644 --- a/core/src/io/anuke/mindustry/entities/enemies/TankEnemy.java +++ b/core/src/io/anuke/mindustry/entities/enemies/TankEnemy.java @@ -18,9 +18,9 @@ public class TankEnemy extends Enemy{ } void shoot(){ - vector.set(length, 0).rotate(direction.angle()); + Angles.translation(angle, 8f); - Angles.shotgun(3, 8f, direction.angle(), f->{ + Angles.shotgun(3, 8f, angle, f->{ Bullet out = new Bullet(bullet, this, x+vector.x, y+vector.y, f).add(); out.damage = (int)(damage*Vars.multiplier); }); diff --git a/core/src/io/anuke/mindustry/io/SaveIO.java b/core/src/io/anuke/mindustry/io/SaveIO.java index bdfbf2bddc..990ae1fac7 100644 --- a/core/src/io/anuke/mindustry/io/SaveIO.java +++ b/core/src/io/anuke/mindustry/io/SaveIO.java @@ -19,9 +19,7 @@ import io.anuke.mindustry.Vars; import io.anuke.mindustry.entities.enemies.*; import io.anuke.mindustry.resource.Item; import io.anuke.mindustry.resource.Weapon; -import io.anuke.mindustry.world.Block; -import io.anuke.mindustry.world.Map; -import io.anuke.mindustry.world.Tile; +import io.anuke.mindustry.world.*; import io.anuke.mindustry.world.blocks.Blocks; import io.anuke.ucore.core.Core; import io.anuke.ucore.entities.Entities; @@ -38,6 +36,8 @@ import io.anuke.ucore.entities.Entities; * Wave (int) * Wave countdown time (float) * + * Gamemode Ordinal (byte) + * * Player X (float) * Player Y (float) * Player health (int) @@ -82,7 +82,7 @@ import io.anuke.ucore.entities.Entities; */ public class SaveIO{ /**Save file version ID. Should be incremented every breaking release.*/ - private static final int fileVersionID = 9; + private static final int fileVersionID = 10; //TODO automatic registration of types? private static final Array> enemyIDs = Array.with( @@ -135,9 +135,21 @@ public class SaveIO{ public static int getWave(int slot){ try(DataInputStream stream = new DataInputStream(fileFor(slot).read())){ - stream.readInt(); - stream.readLong(); - return stream.readInt(); + stream.readInt(); //read version + stream.readLong(); //read last saved time + stream.readByte(); //read the gamemode + return stream.readInt(); //read the wave + }catch (IOException e){ + throw new RuntimeException(e); + } + } + + public static GameMode getMode(int slot){ + + try(DataInputStream stream = new DataInputStream(fileFor(slot).read())){ + stream.readInt(); //read version + stream.readLong(); //read last saved time + return GameMode.values()[stream.readByte()]; //read the gamemode }catch (IOException e){ throw new RuntimeException(e); } @@ -151,10 +163,13 @@ public class SaveIO{ try(DataOutputStream stream = new DataOutputStream(file.write(false))){ + //--META-- stream.writeInt(fileVersionID); //version id - stream.writeLong(TimeUtils.millis()); + stream.writeLong(TimeUtils.millis()); //last saved //--GENERAL STATE-- + stream.writeByte(Vars.control.getMode().ordinal()); //gamemode + stream.writeInt(Vars.control.getWave()); //wave stream.writeFloat(Vars.control.getWaveCountdown()); //wave countdown @@ -270,6 +285,7 @@ public class SaveIO{ } //general state + byte mode = stream.readByte(); int wave = stream.readInt(); float wavetime = stream.readFloat(); @@ -282,6 +298,7 @@ public class SaveIO{ Vars.player.x = playerx; Vars.player.y = playery; Vars.player.health = playerhealth; + Vars.control.setMode(GameMode.values()[mode]); Core.camera.position.set(playerx, playery, 0); //weapons diff --git a/core/src/io/anuke/mindustry/ui/LevelDialog.java b/core/src/io/anuke/mindustry/ui/LevelDialog.java index a6cd5f6c85..e19f697798 100644 --- a/core/src/io/anuke/mindustry/ui/LevelDialog.java +++ b/core/src/io/anuke/mindustry/ui/LevelDialog.java @@ -3,15 +3,16 @@ package io.anuke.mindustry.ui; import com.badlogic.gdx.graphics.g2d.TextureRegion; import io.anuke.mindustry.Vars; +import io.anuke.mindustry.world.GameMode; import io.anuke.mindustry.world.Map; import io.anuke.ucore.core.Core; import io.anuke.ucore.core.Settings; import io.anuke.ucore.core.Timers; import io.anuke.ucore.function.StringSupplier; -import io.anuke.ucore.scene.ui.ImageButton; -import io.anuke.ucore.scene.ui.ScrollPane; +import io.anuke.ucore.scene.ui.*; import io.anuke.ucore.scene.ui.layout.Table; import io.anuke.ucore.scene.ui.layout.Unit; +import io.anuke.ucore.scene.utils.Elements; public class LevelDialog extends FloatingDialog{ private Map selectedMap = Map.delta; @@ -31,6 +32,21 @@ public class LevelDialog extends FloatingDialog{ int maxwidth = 4; + Table selmode = new Table(); + ButtonGroup group = new ButtonGroup<>(); + selmode.add("Gamemode: ").padRight(10f).units(Unit.dp); + + for(GameMode mode : GameMode.values()){ + TextButton b = Elements.newButton(mode.toString(), "toggle", ()->{ + Vars.control.setMode(mode); + }); + group.add(b); + selmode.add(b).size(130f, 54f).units(Unit.dp); + } + + content().add(selmode); + content().row(); + for(int i = 0; i < Map.values().length; i ++){ Map map = Map.values()[i]; @@ -61,7 +77,7 @@ public class LevelDialog extends FloatingDialog{ maps.add(image).width(170).pad(4f).units(Unit.dp); } - content().add(pane); + content().add(pane).uniformX(); shown(()->{ //this is necessary for some reason? diff --git a/core/src/io/anuke/mindustry/ui/LoadDialog.java b/core/src/io/anuke/mindustry/ui/LoadDialog.java index 26b874ad68..1e69e792f6 100644 --- a/core/src/io/anuke/mindustry/ui/LoadDialog.java +++ b/core/src/io/anuke/mindustry/ui/LoadDialog.java @@ -46,8 +46,8 @@ public class LoadDialog extends FloatingDialog{ button.row(); - Label info = new Label("[gray]" + (!SaveIO.isSaveValid(i) ? "" : "Wave " + - SaveIO.getWave(slot)+"\nLast Saved: " + SaveIO.getTimeString(i))); + Label info = new Label("[gray]" + (!SaveIO.isSaveValid(i) ? "" : SaveIO.getMode(slot) + ", Wave " + + SaveIO.getWave(slot) + "\nLast Saved: " + SaveIO.getTimeString(i))); info.setAlignment(Align.center, Align.center); button.add(info).padBottom(2).padTop(6); diff --git a/core/src/io/anuke/mindustry/ui/fragments/BlocksFragment.java b/core/src/io/anuke/mindustry/ui/fragments/BlocksFragment.java index f7f7ab3261..e77c6ef22a 100644 --- a/core/src/io/anuke/mindustry/ui/fragments/BlocksFragment.java +++ b/core/src/io/anuke/mindustry/ui/fragments/BlocksFragment.java @@ -100,7 +100,7 @@ public class BlocksFragment implements Fragment{ image.update(()->{ - boolean canPlace = !control.tutorial.active() || control.tutorial.canPlace(); + boolean canPlace = !control.getTutorial().active() || control.getTutorial().canPlace(); boolean has = control.hasItems(r.requirements) && canPlace; //image.setDisabled(!has); image.setChecked(player.recipe == r); diff --git a/core/src/io/anuke/mindustry/ui/fragments/HudFragment.java b/core/src/io/anuke/mindustry/ui/fragments/HudFragment.java index 581e389c41..e6df62fe3c 100644 --- a/core/src/io/anuke/mindustry/ui/fragments/HudFragment.java +++ b/core/src/io/anuke/mindustry/ui/fragments/HudFragment.java @@ -12,6 +12,7 @@ import io.anuke.mindustry.core.GameState; import io.anuke.mindustry.core.GameState.State; import io.anuke.mindustry.entities.enemies.Enemy; import io.anuke.mindustry.resource.Item; +import io.anuke.mindustry.world.GameMode; import io.anuke.ucore.core.Core; import io.anuke.ucore.core.Draw; import io.anuke.ucore.core.Settings; @@ -73,9 +74,9 @@ public class HudFragment implements Fragment{ //ui table new table(){{ - control.tutorial.buildUI(this); + control.getTutorial().buildUI(this); - visible(()->control.tutorial.active()); + visible(()->control.getTutorial().active()); }}.end(); //paused table @@ -92,6 +93,13 @@ public class HudFragment implements Fragment{ new table(){{ atop(); aright(); + + float uheight = 72f; + + new imagebutton("icon-play", Unit.dp.inPixels(30f), ()->{ + Vars.control.runWave(); + }).size(uheight).uniformY().units(Unit.dp) + .visible(()-> Vars.control.getMode() == GameMode.sandbox && Vars.control.getEnemiesRemaining() <= 0); new table("button"){{ @@ -101,11 +109,11 @@ public class HudFragment implements Fragment{ new label(()-> control.getEnemiesRemaining() > 0 ? control.getEnemiesRemaining() + " Enemies remaining" : - control.tutorial.active() ? "waiting..." : "New wave in " + (int) (control.getWaveCountdown() / 60f)) + (control.getTutorial().active() || Vars.control.getMode() == GameMode.sandbox) ? "waiting..." : "New wave in " + (int) (control.getWaveCountdown() / 60f)) .minWidth(150); get().pad(Unit.dp.inPixels(12)); - }}; + }}.height(uheight).units(Unit.dp); visible(()->!GameState.is(State.menu)); }}.end(); diff --git a/core/src/io/anuke/mindustry/world/GameMode.java b/core/src/io/anuke/mindustry/world/GameMode.java new file mode 100644 index 0000000000..62405136fd --- /dev/null +++ b/core/src/io/anuke/mindustry/world/GameMode.java @@ -0,0 +1,5 @@ +package io.anuke.mindustry.world; + +public enum GameMode{ + waves, sandbox; +} diff --git a/core/src/io/anuke/mindustry/world/blocks/WeaponBlocks.java b/core/src/io/anuke/mindustry/world/blocks/WeaponBlocks.java index b205926b2d..ac4f3969fa 100644 --- a/core/src/io/anuke/mindustry/world/blocks/WeaponBlocks.java +++ b/core/src/io/anuke/mindustry/world/blocks/WeaponBlocks.java @@ -103,6 +103,7 @@ public class WeaponBlocks{ bullet = BulletType.sniper; ammo = Item.steel; health = 70; + shootEffect = Fx.railshot; fullDescription = "Advanced long-range turret. Uses steel for ammo. Very high damage, but low fire rate. " + "Expensive to use, but can be placed far away from enemy lines due to its range."; } @@ -121,6 +122,8 @@ public class WeaponBlocks{ fullDescription = "Advanced splash-damage turret. Uses coal for ammo. " + "Very slow fire rate and bullets, but very high single-target and splash damage. " + "Useful for large crowds of enemies."; + shootEffect = Fx.mortarshot; + shootShake = 2f; } }, @@ -189,6 +192,7 @@ public class WeaponBlocks{ shots = 2; fullDescription = "The ultimate rapid-fire turret. Uses uranium as ammo. Shoots large slugs at a high fire rate. " + "Medium range. Spans multiple tiles. Extremely tough."; + shootEffect = Fx.chainshot; } //TODO specify turret shoot effect in turret instead of doing it manually @@ -203,7 +207,7 @@ public class WeaponBlocks{ for(int i = -1; i < 1; i ++){ Angles.vector.set(len, Mathf.sign(i) * space).rotate(entity.rotation); bullet(tile, entity.rotation); - Effects.effect(Fx.chainshot, tile.worldx() + Angles.x() + offset.x, + Effects.effect(shootEffect, tile.worldx() + Angles.x() + offset.x, tile.worldy()+ Angles.y() + offset.y, entity.rotation); } @@ -225,19 +229,8 @@ public class WeaponBlocks{ shootCone = 9f; fullDescription = "The ultimate long-range turret. Uses uranium as ammo. Shoots large splash-damage shells at a medium rate of fire. " + "Long range. Spans multiple tiles. Extremely tough."; - } - - @Override - protected void shoot(Tile tile){ - TurretEntity entity = tile.entity(); - Vector2 offset = getPlaceOffset(); - - Angles.translation(entity.rotation, 14f); - bullet(tile, entity.rotation); - Effects.effect(Fx.titanshot, tile.worldx() + Angles.x() + offset.x, - tile.worldy()+ Angles.y() + offset.y, entity.rotation); - - Effects.shake(3f, 3f, tile.worldx(), tile.worldy()); + shootEffect = Fx.titanshot; + shootShake = 3f; } }; } diff --git a/core/src/io/anuke/mindustry/world/blocks/types/defense/Turret.java b/core/src/io/anuke/mindustry/world/blocks/types/defense/Turret.java index 83bab1a746..32ef2ec8e8 100644 --- a/core/src/io/anuke/mindustry/world/blocks/types/defense/Turret.java +++ b/core/src/io/anuke/mindustry/world/blocks/types/defense/Turret.java @@ -19,6 +19,7 @@ import io.anuke.mindustry.world.Block; import io.anuke.mindustry.world.Tile; import io.anuke.ucore.core.Draw; import io.anuke.ucore.core.Effects; +import io.anuke.ucore.core.Effects.Effect; import io.anuke.ucore.core.Timers; import io.anuke.ucore.entities.Entities; import io.anuke.ucore.util.Angles; @@ -41,6 +42,8 @@ public class Turret extends Block{ protected int maxammo = 400; protected float rotatespeed = 0.2f; protected float shootCone = 5f; + protected Effect shootEffect = null; + protected float shootShake = 0f; public Turret(String name) { super(name); @@ -216,6 +219,8 @@ public class Turret extends Block{ protected void shoot(Tile tile){ TurretEntity entity = tile.entity(); + Vector2 offset = getPlaceOffset(); + Angles.translation(entity.rotation, width * Vars.tilesize / 2f); for(int i = 0; i < shots; i ++){ @@ -228,12 +233,21 @@ public class Turret extends Block{ } } + + if(shootEffect != null){ + Effects.effect(shootEffect, tile.worldx() + Angles.x() + offset.x, + tile.worldy()+ Angles.y() + offset.y, entity.rotation); + } + + if(shootShake > 0){ + Effects.shake(shootShake, shootShake, tile.entity); + } } protected void bullet(Tile tile, float angle){ Vector2 offset = getPlaceOffset(); - Bullet out = new Bullet(bullet, tile.entity, tile.worldx() + Angles.x() + offset.x, tile.worldy() + Angles.y() + offset.y, angle).add(); - out.damage = (int)(bullet.damage*Vars.multiplier); + Bullet out = new Bullet(bullet, tile.entity, tile.worldx() + Angles.x() + offset.x, tile.worldy() + Angles.y() + offset.y, angle).add(); + out.damage = (int)(bullet.damage*Vars.multiplier); } public static class TurretEntity extends TileEntity{ diff --git a/desktop/mindustry-saves/0.mins b/desktop/mindustry-saves/0.mins index 7bf59da2b4..5df3888dda 100644 Binary files a/desktop/mindustry-saves/0.mins and b/desktop/mindustry-saves/0.mins differ diff --git a/desktop/mindustry-saves/1.mins b/desktop/mindustry-saves/1.mins index 3d5ec95bf7..21c0483e4c 100644 Binary files a/desktop/mindustry-saves/1.mins and b/desktop/mindustry-saves/1.mins differ