Added terrible fog-of-war

This commit is contained in:
Anuken 2018-06-24 00:09:00 -04:00
parent 0267ad574f
commit 77a63a39ad
9 changed files with 123 additions and 23 deletions

View File

@ -0,0 +1,16 @@
#ifdef GL_ES
precision mediump float;
precision mediump int;
#endif
uniform sampler2D u_texture;
varying vec4 v_color;
varying vec2 v_texCoord;
void main() {
vec4 color = texture2D(u_texture, v_texCoord.xy);
color.a = 1.0 - color.r;
color.rgb = vec3(0.0);
gl_FragColor = color * v_color;
}

View File

@ -6,7 +6,9 @@ import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.Texture.TextureWrap; import com.badlogic.gdx.graphics.Texture.TextureWrap;
import com.badlogic.gdx.math.Rectangle; import com.badlogic.gdx.math.Rectangle;
import com.badlogic.gdx.math.Vector2; import com.badlogic.gdx.math.Vector2;
import com.badlogic.gdx.utils.*; import com.badlogic.gdx.utils.ObjectIntMap;
import com.badlogic.gdx.utils.Pools;
import com.badlogic.gdx.utils.TimeUtils;
import io.anuke.mindustry.content.fx.Fx; import io.anuke.mindustry.content.fx.Fx;
import io.anuke.mindustry.core.GameState.State; import io.anuke.mindustry.core.GameState.State;
import io.anuke.mindustry.entities.Player; import io.anuke.mindustry.entities.Player;
@ -29,7 +31,6 @@ import io.anuke.ucore.entities.impl.BaseEntity;
import io.anuke.ucore.entities.impl.EffectEntity; import io.anuke.ucore.entities.impl.EffectEntity;
import io.anuke.ucore.entities.trait.DrawTrait; import io.anuke.ucore.entities.trait.DrawTrait;
import io.anuke.ucore.entities.trait.SolidTrait; import io.anuke.ucore.entities.trait.SolidTrait;
import io.anuke.ucore.function.Callable;
import io.anuke.ucore.function.Consumer; import io.anuke.ucore.function.Consumer;
import io.anuke.ucore.function.Predicate; import io.anuke.ucore.function.Predicate;
import io.anuke.ucore.graphics.Draw; import io.anuke.ucore.graphics.Draw;
@ -50,15 +51,16 @@ public class Renderer extends RendererModule{
private int targetscale = baseCameraScale; private int targetscale = baseCameraScale;
private Texture background = new Texture("sprites/background.png"); private Texture background = new Texture("sprites/background.png");
private FloatArray shieldHits = new FloatArray();
private Array<Callable> shieldDraws = new Array<>();
private Rectangle rect = new Rectangle(), rect2 = new Rectangle(); private Rectangle rect = new Rectangle(), rect2 = new Rectangle();
private Vector2 avgPosition = new Translator(); private Vector2 avgPosition = new Translator();
private Vector2 tmpVector1 = new Translator(); private Vector2 tmpVector1 = new Translator();
private Vector2 tmpVector2 = new Translator(); private Vector2 tmpVector2 = new Translator();
private BlockRenderer blocks = new BlockRenderer(); private BlockRenderer blocks = new BlockRenderer();
private MinimapRenderer minimap = new MinimapRenderer(); private MinimapRenderer minimap = new MinimapRenderer();
private OverlayRenderer overlays = new OverlayRenderer(); private OverlayRenderer overlays = new OverlayRenderer();
private FogRenderer fog = new FogRenderer();
public Renderer() { public Renderer() {
pixelate = true; pixelate = true;
@ -243,8 +245,10 @@ public class Renderer extends RendererModule{
if(showPaths && debug) drawDebug(); if(showPaths && debug) drawDebug();
drawAndInterpolate(playerGroup, p -> !p.isLocal && !p.isDead(), Player::drawName); drawAndInterpolate(playerGroup, p -> !p.isLocal && !p.isDead(), Player::drawName);
batch.end(); batch.end();
fog.draw();
} }
private void drawAllTeams(boolean flying){ private void drawAllTeams(boolean flying){
@ -328,6 +332,7 @@ public class Renderer extends RendererModule{
@Override @Override
public void dispose() { public void dispose() {
background.dispose(); background.dispose();
fog.dispose();
} }
public Vector2 averagePosition(){ public Vector2 averagePosition(){
@ -408,14 +413,6 @@ public class Renderer extends RendererModule{
return blocks; return blocks;
} }
public void addShieldHit(float x, float y){
shieldHits.addAll(x, y, 0f);
}
public void addShield(Callable call){
shieldDraws.add(call);
}
public void setCameraScale(int amount){ public void setCameraScale(int amount){
targetscale = amount; targetscale = amount;
clampScale(); clampScale();

View File

@ -34,11 +34,12 @@ public class EventType {
void handle(); void handle();
} }
/**Called from the logic thread. Do not call graphics here!*/ /**Called from the logic thread. Do not access graphics here!*/
public interface TileChangeEvent extends Event{ public interface TileChangeEvent extends Event{
void handle(Tile tile); void handle(Tile tile);
} }
//TODO unimplemented; remove?
public interface TileRemoveEvent extends Event{ public interface TileRemoveEvent extends Event{
void handle(Tile tile, Team oldTeam); void handle(Tile tile, Team oldTeam);
} }

View File

@ -0,0 +1,81 @@
package io.anuke.mindustry.graphics;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.Pixmap.Format;
import com.badlogic.gdx.graphics.g2d.TextureRegion;
import com.badlogic.gdx.graphics.glutils.FrameBuffer;
import com.badlogic.gdx.utils.Disposable;
import io.anuke.mindustry.entities.Player;
import io.anuke.mindustry.game.EventType.WorldLoadGraphicsEvent;
import io.anuke.ucore.core.Core;
import io.anuke.ucore.core.Events;
import io.anuke.ucore.core.Graphics;
import io.anuke.ucore.graphics.Draw;
import io.anuke.ucore.graphics.Fill;
import static io.anuke.mindustry.Vars.*;
/**Used for rendering fog of war. A framebuffer is used for this.*/
public class FogRenderer implements Disposable{
private TextureRegion region = new TextureRegion();
private FrameBuffer buffer;
public FogRenderer(){
Events.on(WorldLoadGraphicsEvent.class, () -> {
dispose();
buffer = new FrameBuffer(Format.RGBA8888, world.width(), world.height(), false);
//clear buffer to black
buffer.begin();
Graphics.clear(Color.BLACK);
buffer.end();
});
}
public void draw(){
if(buffer == null) return;
float vw = Core.camera.viewportWidth * Core.camera.zoom;
float vh = Core.camera.viewportHeight * Core.camera.zoom;
float px = Core.camera.position.x -= vw/2f;
float py = Core.camera.position.y -= vh/2f;
float u = px / tilesize / world.width();
float v = py / tilesize / world.height();
float u2 = (px + vw)/ tilesize / world.width();
float v2 = (py + vh)/ tilesize / world.height();
Core.batch.getProjectionMatrix().setToOrtho2D(0, 0, world.width() * tilesize, world.height() * tilesize);
Draw.color(Color.WHITE);
buffer.begin();
Graphics.begin();
for(Player player : playerGroup.all()){
Fill.circle(player.x, player.y, 60f);
}
Graphics.end();
buffer.end();
region.setTexture(buffer.getColorBufferTexture());
//region.setRegion(0, 0, 1, 1);
region.setRegion(u, v2, u2, v);
Core.batch.setProjectionMatrix(Core.camera.combined);
Graphics.shader(Shaders.fog);
Graphics.begin();
// Core.batch.draw(buffer.getColorBufferTexture(), px + 50, py, 200, 200 * world.height()/(float)world.width());
Core.batch.draw(region, px, py, vw, vh);
Graphics.end();
Graphics.shader();
}
@Override
public void dispose() {
if(buffer != null) buffer.dispose();
}
}

View File

@ -24,6 +24,7 @@ public class Shaders{
public static UnitBuild build; public static UnitBuild build;
public static MixShader mix; public static MixShader mix;
public static Shader fullMix; public static Shader fullMix;
public static FogShader fog;
public static void init(){ public static void init(){
outline = new Outline(); outline = new Outline();
@ -36,9 +37,16 @@ public class Shaders{
space = new Space(); space = new Space();
build = new UnitBuild(); build = new UnitBuild();
mix = new MixShader(); mix = new MixShader();
fog = new FogShader();
fullMix = new Shader("fullmix", "default"); fullMix = new Shader("fullmix", "default");
} }
public static class FogShader extends Shader{
public FogShader(){
super("fog", "default");
}
}
public static class MixShader extends Shader{ public static class MixShader extends Shader{
public Color color = new Color(Color.WHITE); public Color color = new Color(Color.WHITE);

View File

@ -9,9 +9,6 @@ import io.anuke.ucore.core.Timers;
import io.anuke.ucore.entities.impl.BulletEntity; import io.anuke.ucore.entities.impl.BulletEntity;
import io.anuke.ucore.util.Mathf; import io.anuke.ucore.util.Mathf;
import static io.anuke.mindustry.Vars.headless;
import static io.anuke.mindustry.Vars.renderer;
//TODO remove //TODO remove
public class ShieldBlock extends PowerBlock{ public class ShieldBlock extends PowerBlock{
public float shieldRadius = 40f; public float shieldRadius = 40f;
@ -73,7 +70,7 @@ public class ShieldBlock extends PowerBlock{
bullet.remove(); bullet.remove();
//Effects.effect(bullet.damage > 5 ? BulletFx.shieldhit : BulletFx.laserhit, bullet); //Effects.effect(bullet.damage > 5 ? BulletFx.shieldhit : BulletFx.laserhit, bullet);
if(!headless) renderer.addShieldHit(bullet.x, bullet.y); //if(!headless) renderer.addShieldHit(bullet.x, bullet.y);
entity.power.amount -= bullet.getDamage() * powerPerDamage; entity.power.amount -= bullet.getDamage() * powerPerDamage;
} }

View File

@ -7,7 +7,6 @@ import io.anuke.mindustry.world.blocks.PowerBlock;
import io.anuke.ucore.core.Timers; import io.anuke.ucore.core.Timers;
import io.anuke.ucore.graphics.Draw; import io.anuke.ucore.graphics.Draw;
import static io.anuke.mindustry.Vars.renderer;
import static io.anuke.mindustry.Vars.tilesize; import static io.anuke.mindustry.Vars.tilesize;
//TODO remove //TODO remove
@ -54,7 +53,7 @@ public class ShieldedWallBlock extends PowerBlock{
ShieldedWallEntity entity = tile.entity(); ShieldedWallEntity entity = tile.entity();
if(entity.power.amount > powerPerDamage){ if(entity.power.amount > powerPerDamage){
renderer.addShield(() -> Draw.rect("blank", tile.worldx(), tile.worldy(), tilesize, tilesize)); //renderer.addShield(() -> Draw.rect("blank", tile.worldx(), tile.worldy(), tilesize, tilesize));
} }
Draw.color(hitColor); Draw.color(hitColor);

View File

@ -14,6 +14,7 @@ import static io.anuke.mindustry.Vars.tilesize;
public class CooledTurret extends Turret { public class CooledTurret extends Turret {
/**How much reload is lowered by for each unit of liquid of heat capacity 1.*/ /**How much reload is lowered by for each unit of liquid of heat capacity 1.*/
protected float coolantMultiplier = 1f; protected float coolantMultiplier = 1f;
/**Max coolant used per tick.*/
protected float maxUsed = 1f; protected float maxUsed = 1f;
protected Effect coolEffect = BlockFx.fuelburn; protected Effect coolEffect = BlockFx.fuelburn;

View File

@ -52,8 +52,8 @@ public abstract class Turret extends Block{
protected float recoil = 1f; protected float recoil = 1f;
protected float restitution = 0.02f; protected float restitution = 0.02f;
protected float cooldown = 0.02f; protected float cooldown = 0.02f;
protected float rotatespeed = 0.2f; protected float rotatespeed = 5f; //in degrees per tick
protected float shootCone = 5f; protected float shootCone = 8f;
protected float shootShake = 0f; protected float shootShake = 0f;
protected Translator tr = new Translator(); protected Translator tr = new Translator();
protected Translator tr2 = new Translator(); protected Translator tr2 = new Translator();
@ -168,7 +168,7 @@ public abstract class Turret extends Block{
entity.rotation = 0; entity.rotation = 0;
} }
entity.rotation = Angles.moveToward(entity.rotation, targetRot, 5f * Timers.delta()); entity.rotation = Angles.moveToward(entity.rotation, targetRot, rotatespeed * Timers.delta());
if(Angles.angleDist(entity.rotation, targetRot) < shootCone){ if(Angles.angleDist(entity.rotation, targetRot) < shootCone){
updateShooting(tile); updateShooting(tile);