From 895fa784cf8c2c8399672b75bd7fb1071acb29c8 Mon Sep 17 00:00:00 2001 From: Anuken Date: Sat, 19 Feb 2022 16:24:22 -0500 Subject: [PATCH] Better fog / Research cost tweaks --- core/assets/shaders/fog.frag | 2 +- core/src/mindustry/ai/types/HugAI.java | 4 +- core/src/mindustry/ai/types/SuicideAI.java | 3 +- core/src/mindustry/content/Blocks.java | 3 +- core/src/mindustry/core/World.java | 96 +++++++++---------- core/src/mindustry/entities/Damage.java | 10 +- core/src/mindustry/entities/Lightning.java | 2 +- .../src/mindustry/entities/comp/TeamComp.java | 5 + core/src/mindustry/game/FogControl.java | 39 ++++---- core/src/mindustry/graphics/FogRenderer.java | 68 ++++++++----- .../mindustry/graphics/MinimapRenderer.java | 22 ++++- core/src/mindustry/maps/SectorDamage.java | 3 +- core/src/mindustry/type/UnitType.java | 10 +- .../type/weapons/RepairBeamWeapon.java | 3 +- .../blocks/defense/turrets/BaseTurret.java | 2 + .../world/blocks/power/PowerNode.java | 2 +- .../world/blocks/storage/CoreBlock.java | 1 + 17 files changed, 158 insertions(+), 117 deletions(-) diff --git a/core/assets/shaders/fog.frag b/core/assets/shaders/fog.frag index a44ee7a7e5..6f474c7ddd 100644 --- a/core/assets/shaders/fog.frag +++ b/core/assets/shaders/fog.frag @@ -8,5 +8,5 @@ varying vec2 v_texCoords; void main(){ vec4 color = texture2D(u_texture, v_texCoords.xy); - gl_FragColor = vec4(0.0, 0.0, 0.0, 1.0 - floor(color.r / QUANT) * QUANT); + gl_FragColor = vec4(1.0, 1.0, 1.0, (1.0 - floor(color.r / QUANT) * QUANT) * (step(color.r, 0.99))) * v_color; } diff --git a/core/src/mindustry/ai/types/HugAI.java b/core/src/mindustry/ai/types/HugAI.java index 633f083c47..d6e45467d0 100644 --- a/core/src/mindustry/ai/types/HugAI.java +++ b/core/src/mindustry/ai/types/HugAI.java @@ -2,8 +2,8 @@ package mindustry.ai.types; import arc.math.*; import arc.math.geom.*; -import mindustry.*; import mindustry.ai.*; +import mindustry.core.*; import mindustry.entities.*; import mindustry.entities.units.*; import mindustry.gen.*; @@ -35,7 +35,7 @@ public class HugAI extends AIController{ } //raycast for target - if(target != null && unit.within(target, unit.type.range) && !Vars.world.raycast(unit.tileX(), unit.tileY(), target.tileX(), target.tileY(), (x, y) -> { + if(target != null && unit.within(target, unit.type.range) && !World.raycast(unit.tileX(), unit.tileY(), target.tileX(), target.tileY(), (x, y) -> { for(Point2 p : Geometry.d4c){ if(!unit.canPass(x + p.x, y + p.y)){ return true; diff --git a/core/src/mindustry/ai/types/SuicideAI.java b/core/src/mindustry/ai/types/SuicideAI.java index 7b07f784b3..4f7f9d3ec9 100644 --- a/core/src/mindustry/ai/types/SuicideAI.java +++ b/core/src/mindustry/ai/types/SuicideAI.java @@ -3,6 +3,7 @@ package mindustry.ai.types; import arc.math.geom.*; import mindustry.*; import mindustry.ai.*; +import mindustry.core.*; import mindustry.entities.*; import mindustry.gen.*; import mindustry.world.*; @@ -48,7 +49,7 @@ public class SuicideAI extends GroundAI{ blockedByBlock = false; //raycast for target - boolean blocked = Vars.world.raycast(unit.tileX(), unit.tileY(), target.tileX(), target.tileY(), (x, y) -> { + boolean blocked = World.raycast(unit.tileX(), unit.tileY(), target.tileX(), target.tileY(), (x, y) -> { for(Point2 p : Geometry.d4c){ Tile tile = Vars.world.tile(x + p.x, y + p.y); if(tile != null && tile.build == target) return false; diff --git a/core/src/mindustry/content/Blocks.java b/core/src/mindustry/content/Blocks.java index 514d4787a4..593333b739 100644 --- a/core/src/mindustry/content/Blocks.java +++ b/core/src/mindustry/content/Blocks.java @@ -925,6 +925,7 @@ public class Blocks{ envDisabled = Env.none; itemCapacity = 30; drawer = new DrawArcSmelter(); + researchCostMultiplier = 0.3f; consumeItems(with(Items.graphite, 1, Items.sand, 4)); consumePower(6f); @@ -2481,7 +2482,7 @@ public class Blocks{ cliffCrusher = new WallCrafter("cliff-crusher"){{ requirements(Category.production, with(Items.graphite, 25, Items.beryllium, 20)); - consumePower(0.8f); + consumePower(11 / 60f); drillTime = 110f; size = 2; diff --git a/core/src/mindustry/core/World.java b/core/src/mindustry/core/World.java index 18bc72cdc8..ccd6b8e8a7 100644 --- a/core/src/mindustry/core/World.java +++ b/core/src/mindustry/core/World.java @@ -375,54 +375,6 @@ public class World{ if(invalidMap) Core.app.post(() -> state.set(State.menu)); } - public void raycastEachWorld(float x0, float y0, float x1, float y1, Raycaster cons){ - raycastEach(toTile(x0), toTile(y0), toTile(x1), toTile(y1), cons); - } - - public void raycastEach(int x1, int y1, int x2, int y2, Raycaster cons){ - int x = x1, dx = Math.abs(x2 - x), sx = x < x2 ? 1 : -1; - int y = y1, dy = Math.abs(y2 - y), sy = y < y2 ? 1 : -1; - int e2, err = dx - dy; - - while(true){ - if(cons.accept(x, y)) break; - if(x == x2 && y == y2) break; - - e2 = 2 * err; - if(e2 > -dy){ - err -= dy; - x += sx; - } - - if(e2 < dx){ - err += dx; - y += sy; - } - } - } - - public boolean raycast(int x1, int y1, int x2, int y2, Raycaster cons){ - int x = x1, dx = Math.abs(x2 - x), sx = x < x2 ? 1 : -1; - int y = y1, dy = Math.abs(y2 - y), sy = y < y2 ? 1 : -1; - int e2, err = dx - dy; - - while(true){ - if(cons.accept(x, y)) return true; - if(x == x2 && y == y2) return false; - - e2 = 2 * err; - if(e2 > -dy){ - err = err - dy; - x = x + sx; - } - - if(e2 < dx){ - err = err + dx; - y = y + sy; - } - } - } - public void addDarkness(Tiles tiles){ byte[] dark = new byte[tiles.width * tiles.height]; byte[] writeBuffer = new byte[tiles.width * tiles.height]; @@ -547,6 +499,54 @@ public class World{ return dark; } + public static void raycastEachWorld(float x0, float y0, float x1, float y1, Raycaster cons){ + raycastEach(toTile(x0), toTile(y0), toTile(x1), toTile(y1), cons); + } + + public static void raycastEach(int x1, int y1, int x2, int y2, Raycaster cons){ + int x = x1, dx = Math.abs(x2 - x), sx = x < x2 ? 1 : -1; + int y = y1, dy = Math.abs(y2 - y), sy = y < y2 ? 1 : -1; + int e2, err = dx - dy; + + while(true){ + if(cons.accept(x, y)) break; + if(x == x2 && y == y2) break; + + e2 = 2 * err; + if(e2 > -dy){ + err -= dy; + x += sx; + } + + if(e2 < dx){ + err += dx; + y += sy; + } + } + } + + public static boolean raycast(int x1, int y1, int x2, int y2, Raycaster cons){ + int x = x1, dx = Math.abs(x2 - x), sx = x < x2 ? 1 : -1; + int y = y1, dy = Math.abs(y2 - y), sy = y < y2 ? 1 : -1; + int e2, err = dx - dy; + + while(true){ + if(cons.accept(x, y)) return true; + if(x == x2 && y == y2) return false; + + e2 = 2 * err; + if(e2 > -dy){ + err = err - dy; + x = x + sx; + } + + if(e2 < dx){ + err = err + dx; + y = y + sy; + } + } + } + private class Context implements WorldContext{ Context(){} diff --git a/core/src/mindustry/entities/Damage.java b/core/src/mindustry/entities/Damage.java index 00f69dc6b8..5a8a5ca0d7 100644 --- a/core/src/mindustry/entities/Damage.java +++ b/core/src/mindustry/entities/Damage.java @@ -125,7 +125,7 @@ public class Damage{ public static @Nullable Building findAbsorber(Team team, float x1, float y1, float x2, float y2){ tmpBuilding = null; - boolean found = world.raycast(World.toTile(x1), World.toTile(y1), World.toTile(x2), World.toTile(y2), + boolean found = World.raycast(World.toTile(x1), World.toTile(y1), World.toTile(x2), World.toTile(y2), (x, y) -> (tmpBuilding = world.build(x, y)) != null && tmpBuilding.team != team && tmpBuilding.block.absorbLasers); return found ? tmpBuilding : null; @@ -136,7 +136,7 @@ public class Damage{ furthest = null; - boolean found = world.raycast(b.tileX(), b.tileY(), World.toTile(b.x + Tmp.v1.x), World.toTile(b.y + Tmp.v1.y), + boolean found = World.raycast(b.tileX(), b.tileY(), World.toTile(b.x + Tmp.v1.x), World.toTile(b.y + Tmp.v1.y), (x, y) -> (furthest = world.tile(x, y)) != null && furthest.team() != b.team && (furthest.build != null && furthest.build.absorbLasers())); return found && furthest != null ? Math.max(6f, b.dst(furthest.worldx(), furthest.worldy())) : length; @@ -148,7 +148,7 @@ public class Damage{ furthest = null; pierceCount = 0; - boolean found = world.raycast(b.tileX(), b.tileY(), World.toTile(b.x + Tmp.v1.x), World.toTile(b.y + Tmp.v1.y), + boolean found = World.raycast(b.tileX(), b.tileY(), World.toTile(b.x + Tmp.v1.x), World.toTile(b.y + Tmp.v1.y), (x, y) -> (furthest = world.tile(x, y)) != null && furthest.build != null && furthest.team() != b.team && ++pierceCount >= pierceCap); return found && furthest != null ? Math.max(6f, b.dst(furthest.worldx(), furthest.worldy())) : length; @@ -222,7 +222,7 @@ public class Damage{ if(hitter.type.collidesGround){ seg1.set(x, y); seg2.set(seg1).add(tr); - world.raycastEachWorld(x, y, seg2.x, seg2.y, (cx, cy) -> { + World.raycastEachWorld(x, y, seg2.x, seg2.y, (cx, cy) -> { collider.get(cx, cy); for(Point2 p : Geometry.d4){ @@ -294,7 +294,7 @@ public class Damage{ tmpBuilding = null; if(hitter.type.collidesGround){ - world.raycastEachWorld(x, y, x + tr.x, y + tr.y, (cx, cy) -> { + World.raycastEachWorld(x, y, x + tr.x, y + tr.y, (cx, cy) -> { Building tile = world.build(cx, cy); if(tile != null && tile.team != hitter.team){ tmpBuilding = tile; diff --git a/core/src/mindustry/entities/Lightning.java b/core/src/mindustry/entities/Lightning.java index 29181de687..453150205b 100644 --- a/core/src/mindustry/entities/Lightning.java +++ b/core/src/mindustry/entities/Lightning.java @@ -50,7 +50,7 @@ public class Lightning{ bhit = false; Vec2 from = lines.get(lines.size - 2); Vec2 to = lines.get(lines.size - 1); - world.raycastEach(World.toTile(from.getX()), World.toTile(from.getY()), World.toTile(to.getX()), World.toTile(to.getY()), (wx, wy) -> { + World.raycastEach(World.toTile(from.getX()), World.toTile(from.getY()), World.toTile(to.getX()), World.toTile(to.getY()), (wx, wy) -> { Tile tile = world.tile(wx, wy); if(tile != null && (tile.build != null && tile.build.isInsulated()) && tile.team() != team){ diff --git a/core/src/mindustry/entities/comp/TeamComp.java b/core/src/mindustry/entities/comp/TeamComp.java index b222229619..1193f2ed4a 100644 --- a/core/src/mindustry/entities/comp/TeamComp.java +++ b/core/src/mindustry/entities/comp/TeamComp.java @@ -18,6 +18,11 @@ abstract class TeamComp implements Posc{ return team.rules().cheat; } + /** @return whether the center of this entity is visible to the viewing team. */ + boolean inFogTo(Team viewer){ + return this.team != viewer && !fogControl.isVisible(viewer, x, y); + } + @Nullable public CoreBuild core(){ return team.core(); diff --git a/core/src/mindustry/game/FogControl.java b/core/src/mindustry/game/FogControl.java index 5367e79623..0fcd63944e 100644 --- a/core/src/mindustry/game/FogControl.java +++ b/core/src/mindustry/game/FogControl.java @@ -6,6 +6,7 @@ import arc.struct.*; import arc.util.*; import mindustry.*; import mindustry.annotations.Annotations.*; +import mindustry.core.*; import mindustry.game.EventType.*; import mindustry.gen.*; import mindustry.io.SaveFileReader.*; @@ -63,7 +64,7 @@ public class FogControl implements CustomChunk{ if(state.rules.fog && event.tile.build != null && event.tile.isCenter() && !event.tile.build.team.isAI() && event.tile.block().flags.contains(BlockFlag.hasFogRadius)){ var data = data(event.tile.team()); if(data != null){ - data.dynamicUpdated = data.dynamicUpdatedClient = true; + data.dynamicUpdated = true; } synchronized(staticEvents){ @@ -78,7 +79,7 @@ public class FogControl implements CustomChunk{ if(state.rules.fog && e.tile.build != null && !e.tile.build.team.isAI() && e.tile.block().flags.contains(BlockFlag.hasFogRadius)){ var data = data(e.tile.team()); if(data != null){ - data.dynamicUpdated = data.dynamicUpdatedClient = true; + data.dynamicUpdated = true; } } }); @@ -90,11 +91,16 @@ public class FogControl implements CustomChunk{ return fog == null || fog[team.id] == null ? null : fog[team.id].staticData; } - public boolean isVisible(Team team, int x, int y){ + public boolean isVisible(Team team, float x, float y){ + return isVisibleTile(team, World.toTile(x), World.toTile(y)); + } + + public boolean isVisibleTile(Team team, int x, int y){ if(!state.rules.fog) return true; var data = data(team); - if(data == null || x < 0 || y < 0 || x >= ww || y >= wh) return false; + if(data == null) return true; + if(x < 0 || y < 0 || x >= ww || y >= wh) return false; return data.read.get(x + y * ww); } @@ -161,7 +167,7 @@ public class FogControl implements CustomChunk{ if(data == null){ data = fog[team.team.id] = new FogData(); - data.dynamicUpdated = data.dynamicUpdatedClient = true; + data.dynamicUpdated = true; } synchronized(staticEvents){ @@ -176,27 +182,21 @@ public class FogControl implements CustomChunk{ if(unit.lastFogPos != pos){ pushEvent(event); unit.lastFogPos = pos; - data.dynamicUpdated = data.dynamicUpdatedClient = true; + data.dynamicUpdated = true; } } } - //add building updates (TODO this can run in the if-check, but the renderer needs it...) - for(var build : indexer.getFlagged(team.team, BlockFlag.hasFogRadius)){ - unitEventQueue.add(FogEvent.get(build.tile.x, build.tile.y, build.block.fogRadius, 0)); - } - - //on the client, let the renderer know of all the fog sources - if(data.dynamicUpdatedClient && !headless && team.team == Vars.player.team()){ - renderer.fog.flushDynamic(unitEventQueue); - data.dynamicUpdatedClient = false; - } - //if it's time for an update, flush *everything* onto the update queue if(data.dynamicUpdated && Time.timeSinceMillis(data.lastDynamicMs) > staticUpdateInterval){ data.dynamicUpdated = false; data.lastDynamicMs = Time.millis(); + //add building updates + for(var build : indexer.getFlagged(team.team, BlockFlag.hasFogRadius)){ + dynamicEventQueue.add(FogEvent.get(build.tile.x, build.tile.y, build.block.fogRadius, 0)); + } + //add unit updates dynamicEventQueue.addAll(unitEventQueue); } @@ -405,8 +405,7 @@ public class FogControl implements CustomChunk{ int consec = data & 0b0111_1111; if(sign){ - //TODO disabled for testing? - //bools.set(pos, pos + consec); + bools.set(pos, pos + consec); pos += consec; }else{ pos += consec; @@ -480,8 +479,6 @@ public class FogControl implements CustomChunk{ /** if true, a dynamic fog update must be scheduled. */ boolean dynamicUpdated; - boolean dynamicUpdatedClient; - FogData(){ int len = ww * wh; diff --git a/core/src/mindustry/graphics/FogRenderer.java b/core/src/mindustry/graphics/FogRenderer.java index 6a7f5958de..67fff48043 100644 --- a/core/src/mindustry/graphics/FogRenderer.java +++ b/core/src/mindustry/graphics/FogRenderer.java @@ -12,15 +12,17 @@ import mindustry.game.EventType.*; import mindustry.game.*; import mindustry.gen.*; import mindustry.world.*; +import mindustry.world.meta.*; import static mindustry.Vars.*; /** Highly experimental fog-of-war renderer. */ public class FogRenderer{ + public static final Color + staticColor = new Color(0f, 0f, 0f, 1f), + dynamicColor = new Color(0f, 0f, 0f, 0.5f); private FrameBuffer staticFog = new FrameBuffer(), dynamicFog = new FrameBuffer(); private LongSeq events = new LongSeq(); - private LongSeq dynamics = new LongSeq(); - private boolean dynamicUpdate = false; private Rect rect = new Rect(); private @Nullable Team lastTeam; @@ -35,12 +37,6 @@ public class FogRenderer{ events.add(event); } - public void flushDynamic(LongSeq seq){ - dynamics.clear(); - dynamics.addAll(seq); - dynamicUpdate = true; - } - public Texture getStaticTexture(){ return staticFog.getTexture(); } @@ -54,25 +50,33 @@ public class FogRenderer{ if(fogControl.getDiscovered(player.team()) == null) return; //resize if world size changes - boolean - clearStatic = staticFog.resizeCheck(world.width(), world.height()), - clearDynamic = dynamicFog.resizeCheck(world.width(), world.height()); + boolean clearStatic = staticFog.resizeCheck(world.width(), world.height()); + + dynamicFog.resize(world.width(), world.height()); if(player.team() != lastTeam){ copyFromCpu(); lastTeam = player.team(); clearStatic = false; - dynamicUpdate = true; } - if(clearDynamic || dynamicUpdate){ - dynamicUpdate = false; + //draw dynamic fog every frame + { - Draw.proj(0, 0, staticFog.getWidth(), staticFog.getHeight()); + Core.camera.bounds(Tmp.r1); + Draw.proj(0, 0, staticFog.getWidth() * tilesize, staticFog.getHeight() * tilesize); dynamicFog.begin(Color.black); ScissorStack.push(rect.set(1, 1, staticFog.getWidth() - 2, staticFog.getHeight() - 2)); - //TODO render all (clipped) view circles + Team team = player.team(); + + for(var build : indexer.getFlagged(team, BlockFlag.hasFogRadius)){ + poly(Tmp.r1, build.x, build.y, build.block.fogRadius * tilesize); + } + + for(var unit : team.data().units){ + poly(Tmp.r1, unit.x, unit.y, unit.type.fogRadius * tilesize); + } dynamicFog.end(); ScissorStack.pop(); @@ -95,18 +99,10 @@ public class FogRenderer{ Draw.color(Color.white); - //process new fog events + //process new static fog events for(int i = 0; i < events.size; i++){ - long e = events.items[i]; - Tile tile = world.tile(FogEvent.x(e), FogEvent.y(e)); - float o = 0f; - //visual offset for uneven blocks; this is not reflected on the CPU, but it doesn't really matter - if(tile != null && tile.block().size % 2 == 0 && tile.isCenter()){ - o = 0.5f; - } - Fill.poly(FogEvent.x(e) + 0.5f + o, FogEvent.y(e) + 0.5f + o, 20, FogEvent.radius(e) + 0.3f); + renderEvent(events.items[i]); } - events.clear(); staticFog.end(); @@ -115,12 +111,32 @@ public class FogRenderer{ } staticFog.getTexture().setFilter(TextureFilter.linear); + dynamicFog.getTexture().setFilter(TextureFilter.linear); Draw.shader(Shaders.fog); + Draw.color(dynamicColor); + Draw.fbo(dynamicFog.getTexture(), world.width(), world.height(), tilesize); + Draw.color(staticColor); Draw.fbo(staticFog.getTexture(), world.width(), world.height(), tilesize); Draw.shader(); } + void poly(Rect check, float x, float y, float rad){ + if(check.overlaps(x - rad / 2f, y - rad / 2f, rad * 2f, rad * 2f)){ + Fill.poly(x, y, 20, rad); + } + } + + void renderEvent(long e){ + Tile tile = world.tile(FogEvent.x(e), FogEvent.y(e)); + float o = 0f; + //visual offset for uneven blocks; this is not reflected on the CPU, but it doesn't really matter + if(tile != null && tile.block().size % 2 == 0 && tile.isCenter()){ + o = 0.5f; + } + Fill.poly(FogEvent.x(e) + 0.5f + o, FogEvent.y(e) + 0.5f + o, 20, FogEvent.radius(e) + 0.3f); + } + public void copyFromCpu(){ staticFog.resize(world.width(), world.height()); staticFog.begin(Color.black); diff --git a/core/src/mindustry/graphics/MinimapRenderer.java b/core/src/mindustry/graphics/MinimapRenderer.java index 18e084f76f..c7a0b53e67 100644 --- a/core/src/mindustry/graphics/MinimapRenderer.java +++ b/core/src/mindustry/graphics/MinimapRenderer.java @@ -100,7 +100,7 @@ public class MinimapRenderer{ updateUnitArray(); }else{ units.clear(); - Groups.unit.each(units::add); + Groups.unit.copy(units); } float sz = baseSize * zoom; @@ -112,10 +112,12 @@ public class MinimapRenderer{ rect.set((dx - sz) * tilesize, (dy - sz) * tilesize, sz * 2 * tilesize, sz * 2 * tilesize); for(Unit unit : units){ + if(unit.inFogTo(player.team())) continue; + float rx = !withLabels ? (unit.x - rect.x) / rect.width * w : unit.x / (world.width() * tilesize) * w; float ry = !withLabels ? (unit.y - rect.y) / rect.width * h : unit.y / (world.height() * tilesize) * h; - Draw.mixcol(unit.team().color, 1f); + Draw.mixcol(unit.team.color, 1f); float scale = Scl.scl(1f) / 2f * scaling * 32f; var region = unit.icon(); Draw.rect(region, x + rx, y + ry, scale, scale * (float)region.height / region.width, unit.rotation() - 90); @@ -144,11 +146,23 @@ public class MinimapRenderer{ zoom = z; } Draw.shader(Shaders.fog); - renderer.fog.getStaticTexture().setFilter(TextureFilter.nearest); + Texture staticTex = renderer.fog.getStaticTexture(), dynamicTex = renderer.fog.getDynamicTexture(); + //crisp pixels - Tmp.tr1.set(renderer.fog.getStaticTexture()); + staticTex.setFilter(TextureFilter.nearest); + dynamicTex.setFilter(TextureFilter.nearest); + + Tmp.tr1.set(dynamicTex); Tmp.tr1.set(region.u, 1f - region.v, region.u2, 1f - region.v2); + + Draw.color(FogRenderer.dynamicColor); Draw.rect(Tmp.tr1, x + w/2f, y + h/2f, w, h); + + Tmp.tr1.texture = staticTex; + Draw.color(FogRenderer.staticColor); + Draw.rect(Tmp.tr1, x + w/2f, y + h/2f, w, h); + + Draw.color(); Draw.shader(); } diff --git a/core/src/mindustry/maps/SectorDamage.java b/core/src/mindustry/maps/SectorDamage.java index 84fcc13036..949d62a2e8 100644 --- a/core/src/mindustry/maps/SectorDamage.java +++ b/core/src/mindustry/maps/SectorDamage.java @@ -6,6 +6,7 @@ import arc.struct.*; import arc.util.*; import mindustry.ai.*; import mindustry.content.*; +import mindustry.core.*; import mindustry.entities.*; import mindustry.entities.abilities.*; import mindustry.game.*; @@ -191,7 +192,7 @@ public class SectorDamage{ //TODO would be nice if this worked in a more generic way, with two different calculations and paths if(airOnly){ - world.raycastEach(start.x, start.y, core.tileX(), core.tileY(), (x, y) -> { + World.raycastEach(start.x, start.y, core.tileX(), core.tileY(), (x, y) -> { path.add(world.rawTile(x, y)); return false; }); diff --git a/core/src/mindustry/type/UnitType.java b/core/src/mindustry/type/UnitType.java index 16d7a01b56..fcb2e93820 100644 --- a/core/src/mindustry/type/UnitType.java +++ b/core/src/mindustry/type/UnitType.java @@ -438,10 +438,6 @@ public class UnitType extends UnlockableContent{ lightRadius = Math.max(60f, hitSize * 2.3f); } - if(fogRadius < 0){ - fogRadius = lightRadius * 2f / 8f; - } - clipSize = Math.max(clipSize, lightRadius * 1.1f); singleTarget = weapons.size <= 1 && !forceMultiTarget; @@ -469,6 +465,10 @@ public class UnitType extends UnlockableContent{ } } + if(fogRadius < 0){ + fogRadius = Math.max(lightRadius * 2.5f, 1f) / 8f; + } + if(weapons.isEmpty()){ range = maxRange = miningRange; } @@ -787,6 +787,8 @@ public class UnitType extends UnlockableContent{ //region drawing public void draw(Unit unit){ + if(unit.inFogTo(Vars.player.team())) return; + Mechc mech = unit instanceof Mechc ? (Mechc)unit : null; float z = unit.elevation > 0.5f ? (lowAltitude ? Layer.flyingUnitLow : Layer.flyingUnit) : groundLayer + Mathf.clamp(hitSize / 4000f, 0, 0.01f); diff --git a/core/src/mindustry/type/weapons/RepairBeamWeapon.java b/core/src/mindustry/type/weapons/RepairBeamWeapon.java index 010e32943f..62bc1edc24 100644 --- a/core/src/mindustry/type/weapons/RepairBeamWeapon.java +++ b/core/src/mindustry/type/weapons/RepairBeamWeapon.java @@ -9,6 +9,7 @@ import arc.scene.ui.layout.*; import arc.util.*; import mindustry.*; import mindustry.content.*; +import mindustry.core.*; import mindustry.entities.*; import mindustry.entities.units.*; import mindustry.gen.*; @@ -125,7 +126,7 @@ public class RepairBeamWeapon extends Weapon{ if(targetBuildings){ //snap to closest building - Vars.world.raycastEachWorld(wx, wy, heal.lastEnd.x, heal.lastEnd.y, (x, y) -> { + World.raycastEachWorld(wx, wy, heal.lastEnd.x, heal.lastEnd.y, (x, y) -> { var build = Vars.world.build(x, y); if(build != null && build.team == unit.team && build.damaged()){ heal.target = build; diff --git a/core/src/mindustry/world/blocks/defense/turrets/BaseTurret.java b/core/src/mindustry/world/blocks/defense/turrets/BaseTurret.java index 2fbc9ec7f4..089aea2e79 100644 --- a/core/src/mindustry/world/blocks/defense/turrets/BaseTurret.java +++ b/core/src/mindustry/world/blocks/defense/turrets/BaseTurret.java @@ -1,5 +1,6 @@ package mindustry.world.blocks.defense.turrets; +import arc.math.*; import arc.struct.*; import arc.util.*; import mindustry.content.*; @@ -48,6 +49,7 @@ public class BaseTurret extends Block{ } placeOverlapRange = Math.max(placeOverlapRange, range + placeOverlapMargin); + fogRadius = Math.max(Mathf.round(range / tilesize), fogRadius); super.init(); } diff --git a/core/src/mindustry/world/blocks/power/PowerNode.java b/core/src/mindustry/world/blocks/power/PowerNode.java index 326ed3f95f..90052a1e43 100644 --- a/core/src/mindustry/world/blocks/power/PowerNode.java +++ b/core/src/mindustry/world/blocks/power/PowerNode.java @@ -352,7 +352,7 @@ public class PowerNode extends PowerBlock{ } public static boolean insulated(int x, int y, int x2, int y2){ - return world.raycast(x, y, x2, y2, (wx, wy) -> { + return World.raycast(x, y, x2, y2, (wx, wy) -> { Building tile = world.build(wx, wy); return tile != null && tile.isInsulated(); }); diff --git a/core/src/mindustry/world/blocks/storage/CoreBlock.java b/core/src/mindustry/world/blocks/storage/CoreBlock.java index 2f0aec4685..030de07776 100644 --- a/core/src/mindustry/world/blocks/storage/CoreBlock.java +++ b/core/src/mindustry/world/blocks/storage/CoreBlock.java @@ -104,6 +104,7 @@ public class CoreBlock extends StorageBlock{ public void init(){ //assign to update clipSize internally lightRadius = 30f + 20f * size; + fogRadius = Math.max(fogRadius, (int)(lightRadius / 8f * 2f)); emitLight = true; super.init();