Added VTOL animation

This commit is contained in:
Anuken 2018-04-29 01:22:26 -04:00
parent d0a44906fe
commit b589d8a1df
19 changed files with 201 additions and 56 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 203 B

After

Width:  |  Height:  |  Size: 203 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 191 B

After

Width:  |  Height:  |  Size: 185 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 106 KiB

After

Width:  |  Height:  |  Size: 106 KiB

View File

@ -4,6 +4,7 @@ import io.anuke.mindustry.content.Items;
import io.anuke.mindustry.content.UnitTypes;
import io.anuke.mindustry.resource.ItemStack;
import io.anuke.mindustry.world.Block;
import io.anuke.mindustry.world.blocks.types.units.ResupplyPoint;
import io.anuke.mindustry.world.blocks.types.units.UnitFactory;
public class UnitBlocks {
@ -34,5 +35,10 @@ public class UnitBlocks {
requirements = new ItemStack[]{
new ItemStack(Items.stone, 1)
};
}},
resupplyPoint = new ResupplyPoint("resupplypoint"){{
size = 2;
itemCapacity = 30;
}};
}

View File

@ -2,6 +2,7 @@ package io.anuke.mindustry.content.fx;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.Colors;
import io.anuke.mindustry.graphics.Palette;
import io.anuke.ucore.core.Effects.Effect;
import io.anuke.ucore.graphics.Draw;
import io.anuke.ucore.graphics.Fill;
@ -36,13 +37,6 @@ public class Fx{
Draw.reset();
}),
dash = new Effect(30, e -> {
Draw.color(Color.CORAL, Color.GRAY, e.fin());
float size = e.fout()*4f;
Draw.rect("circle", e.x, e.y, size, size);
Draw.reset();
}),
spawn = new Effect(23, e -> {
Lines.stroke(2f);
Draw.color(Color.DARK_GRAY, Color.SCARLET, e.fin());

View File

@ -0,0 +1,20 @@
package io.anuke.mindustry.content.fx;
import io.anuke.mindustry.graphics.Palette;
import io.anuke.ucore.core.Effects.Effect;
import io.anuke.ucore.graphics.Draw;
import io.anuke.ucore.graphics.Fill;
import io.anuke.ucore.util.Angles;
import io.anuke.ucore.util.Mathf;
public class UnitFx {
public static final Effect
vtolHover = new Effect(40f, e -> {
float len = e.finpow()*10f;
float ang = e.rotation + Mathf.randomSeedRange(e.id, 30f);
Draw.color(Palette.lightFlame);
Fill.circle(e.x + Angles.trnsx(ang, len), e.y + Angles.trnsy(ang, len), 2f * e.fout());
Draw.reset();
});
}

View File

@ -60,9 +60,9 @@ public class ContentLoader {
//TODO 128 blocks!
Log.info("--- CONTENT INFO ---");
Log.info("Blocks loaded: {0}\nItems loaded: {1}\nLiquids loaded: {2}\nUpgrades loaded: {3}\nUnits loaded: {4}\nAmmo types loaded: {5}\nStatus effects loaded: {6}",
Log.info("Blocks loaded: {0}\nItems loaded: {1}\nLiquids loaded: {2}\nUpgrades loaded: {3}\nUnits loaded: {4}\nAmmo types loaded: {5}\nStatus effects loaded: {6}\nTotal content classes: {7}",
Block.getAllBlocks().size, Item.getAllItems().size, Liquid.getAllLiquids().size,
Mech.getAllUpgrades().size, UnitType.getAllTypes().size, AmmoType.getAllTypes().size, StatusEffect.getAllEffects().size);
Mech.getAllUpgrades().size, UnitType.getAllTypes().size, AmmoType.getAllTypes().size, StatusEffect.getAllEffects().size, content.length);
Log.info("-------------------");
}

View File

@ -33,7 +33,7 @@ import static io.anuke.mindustry.Vars.*;
/**Control module.
* Handles all input, saving, keybinds and keybinds.
* Should <i>not</i> handle any game-critical state.
* Should <i>not</i> handle any logic-critical state.
* This class is not created in the headless server.*/
public class Control extends Module{
private Tutorial tutorial = new Tutorial();

View File

@ -251,22 +251,21 @@ public class Renderer extends RendererModule{
if(group.count(p -> p.isFlying() == flying) +
playerGroup.count(p -> p.isFlying() == flying && p.team == team) == 0 && flying) continue;
Entities.drawWith(unitGroups[team.ordinal()], u -> u.isFlying() == flying, Unit::drawUnder);
Entities.drawWith(playerGroup, p -> p.isFlying() == flying && p.team == team, Unit::drawUnder);
Shaders.outline.color.set(team.color);
Graphics.beginShaders(Shaders.outline);
Graphics.shader(Shaders.hit, false);
drawTeam(team, flying);
Entities.draw(unitGroups[team.ordinal()], u -> u.isFlying() == flying);
Entities.draw(playerGroup, p -> p.isFlying() == flying && p.team == team);
Graphics.shader();
blocks.drawTeamBlocks(Layer.turret, team);
Graphics.endShaders();
}
}
private void drawTeam(Team team, boolean flying){
Entities.draw(unitGroups[team.ordinal()], u -> u.isFlying() == flying);
Entities.draw(playerGroup, p -> p.isFlying() == flying && p.team == team);
}
@Override
public void resize(int width, int height){
super.resize(width, height);
@ -533,6 +532,8 @@ public class Renderer extends RendererModule{
}
void drawStats(Unit unit){
if(unit.isDead()) return;
float x = unit.getDrawPosition().x;
float y = unit.getDrawPosition().y;
@ -541,8 +542,9 @@ public class Renderer extends RendererModule{
y = (int)y;
}
drawBar(Color.SCARLET, x, y - 7f, unit.health / unit.maxhealth);
drawBar(Color.valueOf("32cf6d"), x, y - 8f, unit.inventory.totalAmmo() / (float) unit.inventory.ammoCapacity());
drawEncloser(x, y - 8f, 2f);
drawBar(Color.SCARLET, x, y - 8f, unit.health / unit.maxhealth);
drawBar(Color.valueOf("32cf6d"), x, y - 9f, unit.inventory.totalAmmo() / (float) unit.inventory.ammoCapacity());
}
//TODO optimize!
@ -557,12 +559,6 @@ public class Renderer extends RendererModule{
x -= 0.5f;
y += 0.5f;
/*
Lines.stroke(3f);
Draw.color(Color.SLATE);
Lines.line(x - len + 1, y, x + len + 1.5f, y);
Lines.stroke(1f);*/
Draw.color(Color.BLACK);
Lines.line(x - len + 1, y, x + len + 0.5f, y);
@ -572,6 +568,19 @@ public class Renderer extends RendererModule{
Draw.reset();
}
public void drawEncloser(float x, float y, float height){
x -= 0.5f;
y += 0.5f - (height-1f)/2f;
float len = 3;
Lines.stroke(2f + height);
Draw.color(Color.SLATE);
Lines.line(x - len - 0.5f, y, x + len + 1.5f, y, CapStyle.none);
Draw.reset();
}
public void setCameraScale(int amount){
targetscale = amount;
clampScale();

View File

@ -6,7 +6,6 @@ import com.badlogic.gdx.utils.Array;
import io.anuke.mindustry.content.Mechs;
import io.anuke.mindustry.content.Weapons;
import io.anuke.mindustry.content.fx.ExplosionFx;
import io.anuke.mindustry.content.fx.Fx;
import io.anuke.mindustry.entities.effect.DamageArea;
import io.anuke.mindustry.game.Team;
import io.anuke.mindustry.graphics.Palette;
@ -271,10 +270,6 @@ public class Player extends Unit{
weapon.update(player, false);
}
if(dashing && timer.get(timerDash, 3) && movement.len() > 0){
Effects.effect(Fx.dash, x + Angles.trnsx(rotation + 180f, 3f), y + Angles.trnsy(rotation + 180f, 3f));
}
movement.limit(speed);
velocity.add(movement);
@ -326,6 +321,11 @@ public class Player extends Unit{
if(isLocal){
super.writeSave(stream);
stream.writeByte(upgrades.size);
for(Upgrade u : upgrades){
stream.writeByte(u.id);
}
}
}
@ -340,13 +340,18 @@ public class Player extends Unit{
private void readSaveSuper(DataInputStream stream) throws IOException {
super.readSave(stream);
byte uamount = stream.readByte();
for (int i = 0; i < uamount; i++) {
upgrades.add(Upgrade.getByID(stream.readByte()));
}
add();
}
@Override
public void writeSpawn(ByteBuffer buffer) {
buffer.put((byte)name.getBytes().length);
buffer.put(name.getBytes());
IOUtils.writeString(buffer, name);
buffer.put(weapon.id);
buffer.put(mech.id);
buffer.put(isAdmin ? 1 : (byte)0);
@ -358,10 +363,7 @@ public class Player extends Unit{
@Override
public void readSpawn(ByteBuffer buffer) {
byte nlength = buffer.get();
byte[] n = new byte[nlength];
buffer.get(n);
name = new String(n);
name = IOUtils.readString(buffer);
weapon = Upgrade.getByID(buffer.get());
mech = Upgrade.getByID(buffer.get());
isAdmin = buffer.get() == 1;
@ -410,14 +412,6 @@ public class Player extends Unit{
float tx = x + Angles.trnsx(rotation + 180f, 4f);
float ty = y + Angles.trnsy(rotation + 180f, 4f);
if(mech.flying && i.target.dst(i.last) > 2f && timer.get(timerDash, 1)){
Effects.effect(Fx.dash, tx, ty);
}
if(dashing && !dead && timer.get(timerDash, 3) && i.target.dst(i.last) > 1f){
Effects.effect(Fx.dash, tx, ty);
}
}
public Color getColor(){

View File

@ -20,9 +20,9 @@ public abstract class SyncEntity extends DestructibleEntity{
private Vector3 spos = new Vector3();
/**rotation of the top, usually used as the 'shoot' direction.*/
public float rotation;
public float rotation = 90;
/**rotation of the base, usually leg rotation for mechs.*/
public float baseRotation;
public float baseRotation = 90;
/**Called when a death event is recieved remotely.*/
public abstract void onRemoteDeath();

View File

@ -26,7 +26,7 @@ public abstract class Unit extends SyncEntity implements SerializableEntity {
public UnitInventory inventory = new UnitInventory(100, 100);
public Team team = Team.blue;
public Vector2 velocity = new Vector2();
public Vector2 velocity = new Vector2(0f, 0.0001f);
public float hitTime;
public float drownTime;
@ -148,6 +148,8 @@ public abstract class Unit extends SyncEntity implements SerializableEntity {
}
}
public void drawUnder(){}
public abstract boolean acceptsAmmo(Item item);
public abstract void addAmmo(Item item);
public abstract float getMass();

View File

@ -7,7 +7,10 @@ import io.anuke.mindustry.entities.BulletType;
import io.anuke.mindustry.entities.Unit;
import io.anuke.mindustry.game.Team;
import io.anuke.mindustry.resource.Item;
import io.anuke.ucore.core.Effects;
import io.anuke.ucore.core.Effects.Effect;
import io.anuke.ucore.entities.Entity;
import io.anuke.ucore.util.Angles;
import io.anuke.ucore.util.Mathf;
import io.anuke.ucore.util.Timer;
@ -40,6 +43,12 @@ public class BaseUnit extends Unit{
rotation = Mathf.slerpDelta(rotation, angle, type.rotatespeed);
}
public void effectAt(Effect effect, float rotation, float dx, float dy){
Effects.effect(effect,
x + Angles.trnsx(rotation, dx, dy),
y + Angles.trnsy(rotation, dx, dy), Mathf.atan2(dx, dy));
}
@Override
public boolean acceptsAmmo(Item item) {
return type.ammo.containsKey(item) && inventory.canAcceptAmmo(type.ammo.get(item));
@ -81,6 +90,12 @@ public class BaseUnit extends Unit{
type.draw(this);
}
@Override
public void drawUnder(){
type.drawUnder(this);
}
@Override
public float drawSize(){
return 14;

View File

@ -2,20 +2,17 @@ package io.anuke.mindustry.entities.units;
import com.badlogic.gdx.math.Vector2;
import com.badlogic.gdx.utils.ObjectSet;
import io.anuke.mindustry.content.fx.Fx;
import io.anuke.mindustry.entities.Unit;
import io.anuke.mindustry.game.TeamInfo.TeamData;
import io.anuke.mindustry.resource.AmmoType;
import io.anuke.mindustry.world.Tile;
import io.anuke.ucore.core.Effects;
import io.anuke.ucore.core.Timers;
import io.anuke.ucore.graphics.Draw;
import io.anuke.ucore.util.Angles;
import static io.anuke.mindustry.Vars.state;
public class FlyingUnitType extends UnitType {
private static Vector2 vec = new Vector2();
protected static Vector2 vec = new Vector2();
protected float boosterLength = 4.5f;
@ -34,8 +31,8 @@ public class FlyingUnitType extends UnitType {
unit.rotation = unit.velocity.angle();
if(unit.velocity.len() > 0.2f && unit.timer.get(timerBoost, 2f)){
Effects.effect(Fx.dash, unit.x + Angles.trnsx(unit.rotation + 180f, boosterLength),
unit.y + Angles.trnsy(unit.rotation + 180f, boosterLength));
//Effects.effect(UnitFx.vtolHover, unit.x + Angles.trnsx(unit.rotation + 180f, boosterLength),
// unit.y + Angles.trnsy(unit.rotation + 180f, boosterLength));
}
}

View File

@ -59,6 +59,8 @@ public abstract class UnitType {
public abstract void draw(BaseUnit unit);
public void drawUnder(BaseUnit unit){}
public boolean isFlying(){
return isFlying;
}

View File

@ -1,10 +1,15 @@
package io.anuke.mindustry.entities.units.types;
import com.badlogic.gdx.graphics.Color;
import io.anuke.mindustry.content.AmmoTypes;
import io.anuke.mindustry.entities.Unit;
import io.anuke.mindustry.entities.units.BaseUnit;
import io.anuke.mindustry.entities.units.FlyingUnitType;
import io.anuke.mindustry.graphics.Palette;
import io.anuke.ucore.core.Timers;
import io.anuke.ucore.graphics.Draw;
import io.anuke.ucore.graphics.Fill;
import io.anuke.ucore.util.Angles;
import io.anuke.ucore.util.Mathf;
public class Vtol extends FlyingUnitType {
@ -14,16 +19,70 @@ public class Vtol extends FlyingUnitType {
setAmmo(AmmoTypes.basicIron);
}
@Override
public void drawUnder(BaseUnit unit) {
for(int i : Mathf.signs) {
float rotation = unit.rotation - 90;
float dx = 5f * i, dx2 = 6f * i;
float dy = 4f, dy2 = -5f;
float rad = 1.5f + Mathf.absin(Timers.time(), 3f, 0.6f);
float ds = 1.2f;
Draw.color(Palette.lightishOrange, Palette.lightFlame, Mathf.absin(Timers.time(), 3f, 0.3f));
Fill.circle(
unit.x + Angles.trnsx(rotation, dx, dy),
unit.y + Angles.trnsy(rotation, dx, dy), rad);
Fill.circle(
unit.x + Angles.trnsx(rotation, dx2, dy2),
unit.y + Angles.trnsy(rotation, dx2, dy2), rad);
Draw.color(Color.GRAY);
Fill.circle(
unit.x + Angles.trnsx(rotation, dx, dy)/ds,
unit.y + Angles.trnsy(rotation, dx, dy)/ds, 2f);
Fill.circle(
unit.x + Angles.trnsx(rotation, dx2, dy2)/ds,
unit.y + Angles.trnsy(rotation, dx2, dy2)/ds, 2f);
Draw.color(Color.WHITE);
}
}
@Override
public void draw(BaseUnit unit) {
Draw.alpha(unit.hitTime / Unit.hitDuration);
Draw.rect(name, unit.x, unit.y, unit.rotation - 90);
for(int i : Mathf.signs){
Draw.rect(name + "-booster-1", unit.x, unit.y, 12*i, 12, unit.rotation - 90);
Draw.rect(name + "-booster-2", unit.x, unit.y, 12*i, 12, unit.rotation - 90);
Draw.rect(name + "-booster-1", unit.x + i, unit.y, 12*i, 12, unit.rotation - 90);
Draw.rect(name + "-booster-2", unit.x + i, unit.y, 12*i, 12, unit.rotation - 90);
}
Draw.alpha(1f);
}
@Override
public void update(BaseUnit unit) {
super.update(unit);
unit.x += Mathf.sin(Timers.time() + unit.id*999, 25f, 0.07f);
unit.y += Mathf.cos(Timers.time() + unit.id*999, 25f, 0.07f);
unit.rotation += Mathf.sin(Timers.time() + unit.id*99, 10f, 8f);
}
@Override
public void behavior(BaseUnit unit) {
//super.behavior(unit);
}
}

View File

@ -12,6 +12,7 @@ public class Palette {
public static final Color turretHeat = Color.valueOf("ab3400");
public static final Color lightOrange = Color.valueOf("f68021");
public static final Color lightishOrange = Color.valueOf("f8ad42");
public static final Color lighterOrange = Color.valueOf("f6e096");
public static final Color lightishGray = Color.valueOf("a2a2a2");

View File

@ -1,4 +1,50 @@
package io.anuke.mindustry.world.blocks.types.units;
public class ResupplyPoint {
import com.badlogic.gdx.math.Rectangle;
import io.anuke.mindustry.entities.Units;
import io.anuke.mindustry.entities.effect.ItemTransferEffect;
import io.anuke.mindustry.resource.Item;
import io.anuke.mindustry.world.Block;
import io.anuke.mindustry.world.Tile;
public class ResupplyPoint extends Block{
private static Rectangle rect = new Rectangle();
protected int timerSupply = timers ++;
protected float supplyRadius = 50f;
protected float supplyInterval = 5f;
public ResupplyPoint(String name) {
super(name);
update = true;
solid = true;
}
@Override
public void update(Tile tile) {
if(tile.entity.timer.get(timerSupply, supplyInterval)){
rect.setSize(supplyRadius*2).setCenter(tile.drawx(), tile.drawy());
Units.getNearby(tile.getTeam(), rect, unit -> {
if(unit.distanceTo(tile.drawx(), tile.drawy()) > supplyRadius) return;
for(int i = 0; i < tile.entity.items.items.length; i ++){
Item item = Item.getByID(i);
if(tile.entity.items.items[i] > 0 && unit.acceptsAmmo(item)){
tile.entity.items.items[i] --;
unit.addAmmo(item);
new ItemTransferEffect(item, tile.drawx(), tile.drawy(), unit).add();
return;
}
}
});
}
}
@Override
public boolean acceptItem(Item item, Tile tile, Tile source) {
return tile.entity.items.totalItems() < itemCapacity;
}
}

View File

@ -38,7 +38,7 @@ public class UnitFactory extends Block {
protected float produceTime = 1000f;
protected float powerUse = 0.1f;
protected float openDuration = 50f;
protected float launchVelocity = 4f;
protected float launchVelocity = 0f;
protected String unitRegion;
public UnitFactory(String name) {