Implemented entity spawning and despawning and changed some stuff
- Non-player entities can now be added and removed properly - WorldLogic.spawnEntity can be used to add entity and create an entity ID - Statie is back, more beautiful than ever! - Place Test:StatieSpawner block and wait to make her spawn - TPS display now features a visual tick indicator - Updated Fern texture
This commit is contained in:
parent
c7e7d3bdac
commit
1d28f32865
@ -260,6 +260,18 @@ public class Shapes {
|
|||||||
return this.setSize(size, size, size);
|
return this.setSize(size, size, size);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public PppBuilder centerAt(float x, float y, float z) {
|
||||||
|
origin.set(x, y, z);
|
||||||
|
|
||||||
|
origin.mul(2);
|
||||||
|
origin.sub(width);
|
||||||
|
origin.sub(height);
|
||||||
|
origin.sub(depth);
|
||||||
|
origin.div(2);
|
||||||
|
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
public PppBuilder flip() {
|
public PppBuilder flip() {
|
||||||
this.flip = true;
|
this.flip = true;
|
||||||
return this;
|
return this;
|
||||||
|
@ -145,7 +145,7 @@ public class ClientManager {
|
|||||||
return;
|
return;
|
||||||
if (!(c instanceof ClientPlayer))
|
if (!(c instanceof ClientPlayer))
|
||||||
return;
|
return;
|
||||||
if (!((ClientPlayer) c).isChunkVisible(entityId))
|
if (!((ClientPlayer) c).isEntityVisible(entityId))
|
||||||
return;
|
return;
|
||||||
c.sendPacket(packet);
|
c.sendPacket(packet);
|
||||||
});
|
});
|
||||||
|
@ -19,6 +19,9 @@
|
|||||||
package ru.windcorp.progressia.server.comms;
|
package ru.windcorp.progressia.server.comms;
|
||||||
|
|
||||||
import glm.vec._3.i.Vec3i;
|
import glm.vec._3.i.Vec3i;
|
||||||
|
import gnu.trove.TCollections;
|
||||||
|
import gnu.trove.set.TLongSet;
|
||||||
|
import gnu.trove.set.hash.TLongHashSet;
|
||||||
import ru.windcorp.progressia.common.world.generic.ChunkSet;
|
import ru.windcorp.progressia.common.world.generic.ChunkSet;
|
||||||
import ru.windcorp.progressia.common.world.generic.ChunkSets;
|
import ru.windcorp.progressia.common.world.generic.ChunkSets;
|
||||||
import ru.windcorp.progressia.server.Player;
|
import ru.windcorp.progressia.server.Player;
|
||||||
@ -53,8 +56,19 @@ public abstract class ClientPlayer extends ClientChat {
|
|||||||
return player.getServer().getLoadManager().getVisionManager().getVisibleChunks(player);
|
return player.getServer().getLoadManager().getVisionManager().getVisibleChunks(player);
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isChunkVisible(long entityId) {
|
public boolean isEntityVisible(long entityId) {
|
||||||
return true;
|
if (player == null)
|
||||||
|
return false;
|
||||||
|
return player.getServer().getLoadManager().getVisionManager().isEntityVisible(entityId, player);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final TLongSet EMPTY_TLONGSET = TCollections.unmodifiableSet(new TLongHashSet(0));
|
||||||
|
|
||||||
|
public TLongSet getVisibleEntities(Player player) {
|
||||||
|
if (player == null) {
|
||||||
|
return EMPTY_TLONGSET;
|
||||||
|
}
|
||||||
|
return player.getServer().getLoadManager().getVisionManager().getVisibleEntities(player);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -17,10 +17,14 @@
|
|||||||
*/
|
*/
|
||||||
package ru.windcorp.progressia.server.management.load;
|
package ru.windcorp.progressia.server.management.load;
|
||||||
|
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import glm.vec._3.i.Vec3i;
|
import glm.vec._3.i.Vec3i;
|
||||||
import ru.windcorp.progressia.common.world.DefaultChunkData;
|
import ru.windcorp.progressia.common.world.DefaultChunkData;
|
||||||
import ru.windcorp.progressia.common.world.PacketRevokeChunk;
|
import ru.windcorp.progressia.common.world.PacketRevokeChunk;
|
||||||
import ru.windcorp.progressia.common.world.PacketSendChunk;
|
import ru.windcorp.progressia.common.world.PacketSendChunk;
|
||||||
|
import ru.windcorp.progressia.common.world.entity.EntityData;
|
||||||
import ru.windcorp.progressia.common.world.DefaultWorldData;
|
import ru.windcorp.progressia.common.world.DefaultWorldData;
|
||||||
import ru.windcorp.progressia.server.Player;
|
import ru.windcorp.progressia.server.Player;
|
||||||
import ru.windcorp.progressia.server.Server;
|
import ru.windcorp.progressia.server.Server;
|
||||||
@ -140,6 +144,11 @@ public class ChunkManager {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO allow entities to be saved first
|
||||||
|
Set<EntityData> entitiesToRemove = new HashSet<>();
|
||||||
|
world.forEachEntityInChunk(chunkPos, entitiesToRemove::add);
|
||||||
|
entitiesToRemove.forEach(world::removeEntity);
|
||||||
|
|
||||||
world.removeChunk(chunk);
|
world.removeChunk(chunk);
|
||||||
TestWorldDiskIO.saveChunk(chunk, getServer());
|
TestWorldDiskIO.saveChunk(chunk, getServer());
|
||||||
|
|
||||||
|
@ -25,6 +25,9 @@ import java.util.function.Consumer;
|
|||||||
import com.google.common.eventbus.Subscribe;
|
import com.google.common.eventbus.Subscribe;
|
||||||
|
|
||||||
import glm.vec._3.i.Vec3i;
|
import glm.vec._3.i.Vec3i;
|
||||||
|
import gnu.trove.TCollections;
|
||||||
|
import gnu.trove.set.TLongSet;
|
||||||
|
import gnu.trove.set.hash.TLongHashSet;
|
||||||
import ru.windcorp.progressia.common.world.generic.ChunkSet;
|
import ru.windcorp.progressia.common.world.generic.ChunkSet;
|
||||||
import ru.windcorp.progressia.common.world.generic.ChunkSets;
|
import ru.windcorp.progressia.common.world.generic.ChunkSets;
|
||||||
import ru.windcorp.progressia.server.Player;
|
import ru.windcorp.progressia.server.Player;
|
||||||
@ -85,6 +88,28 @@ public class VisionManager {
|
|||||||
return vision.getVisibleChunks();
|
return vision.getVisibleChunks();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isEntityVisible(long entityId, Player player) {
|
||||||
|
PlayerVision vision = getVision(player, false);
|
||||||
|
|
||||||
|
if (vision == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return vision.isEntityVisible(entityId);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final TLongSet EMPTY_TLONGSET = TCollections.unmodifiableSet(new TLongHashSet(0));
|
||||||
|
|
||||||
|
public TLongSet getVisibleEntities(Player player) {
|
||||||
|
PlayerVision vision = getVision(player, false);
|
||||||
|
|
||||||
|
if (vision == null) {
|
||||||
|
return EMPTY_TLONGSET;
|
||||||
|
}
|
||||||
|
|
||||||
|
return vision.getVisibleEntities();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return the loadManager
|
* @return the loadManager
|
||||||
*/
|
*/
|
||||||
|
@ -21,6 +21,7 @@ package ru.windcorp.progressia.server.world;
|
|||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
import glm.Glm;
|
import glm.Glm;
|
||||||
import glm.vec._3.i.Vec3i;
|
import glm.vec._3.i.Vec3i;
|
||||||
@ -89,6 +90,27 @@ public class DefaultWorldLogic implements WorldLogic {
|
|||||||
return getData().getEntity(entityId);
|
return getData().getEntity(entityId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void spawnEntity(EntityData entity) {
|
||||||
|
Objects.requireNonNull(entity, "entity");
|
||||||
|
if (entity.getEntityId() != EntityData.NULL_ENTITY_ID) {
|
||||||
|
throw new IllegalArgumentException(
|
||||||
|
"Entity ID of entity " + entity
|
||||||
|
+ " is not unassigned; use WorldData.addEntity to add entity with assigned entity ID"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
long entityId;
|
||||||
|
|
||||||
|
// TODO this should be synchronized on the entity set
|
||||||
|
do {
|
||||||
|
entityId = server.getAdHocRandom().nextLong();
|
||||||
|
} while (entityId == EntityData.NULL_ENTITY_ID || getEntity(entityId) != null);
|
||||||
|
|
||||||
|
entity.setEntityId(entityId);
|
||||||
|
getData().addEntity(entity);
|
||||||
|
}
|
||||||
|
|
||||||
public Evaluation getTickEntitiesTask() {
|
public Evaluation getTickEntitiesTask() {
|
||||||
return tickEntitiesTask;
|
return tickEntitiesTask;
|
||||||
}
|
}
|
||||||
@ -110,31 +132,49 @@ public class DefaultWorldLogic implements WorldLogic {
|
|||||||
DefaultChunkData chunk = getGenerator().generate(chunkPos);
|
DefaultChunkData chunk = getGenerator().generate(chunkPos);
|
||||||
|
|
||||||
if (!Glm.equals(chunkPos, chunk.getPosition())) {
|
if (!Glm.equals(chunkPos, chunk.getPosition())) {
|
||||||
throw CrashReports.report(null, "Generator %s has generated a chunk at (%d; %d; %d) when requested to generate a chunk at (%d; %d; %d)",
|
throw CrashReports.report(
|
||||||
|
null,
|
||||||
|
"Generator %s has generated a chunk at (%d; %d; %d) when requested to generate a chunk at (%d; %d; %d)",
|
||||||
getGenerator(),
|
getGenerator(),
|
||||||
chunk.getX(), chunk.getY(), chunk.getZ(),
|
chunk.getX(),
|
||||||
chunkPos.x, chunkPos.y, chunkPos.z
|
chunk.getY(),
|
||||||
|
chunk.getZ(),
|
||||||
|
chunkPos.x,
|
||||||
|
chunkPos.y,
|
||||||
|
chunkPos.z
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (getData().getChunk(chunk.getPosition()) != chunk) {
|
if (getData().getChunk(chunk.getPosition()) != chunk) {
|
||||||
if (isChunkLoaded(chunkPos)) {
|
if (isChunkLoaded(chunkPos)) {
|
||||||
throw CrashReports.report(null, "Generator %s has returned a chunk different to the chunk that is located at (%d; %d; %d)",
|
throw CrashReports.report(
|
||||||
|
null,
|
||||||
|
"Generator %s has returned a chunk different to the chunk that is located at (%d; %d; %d)",
|
||||||
getGenerator(),
|
getGenerator(),
|
||||||
chunkPos.x, chunkPos.y, chunkPos.z
|
chunkPos.x,
|
||||||
|
chunkPos.y,
|
||||||
|
chunkPos.z
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
throw CrashReports.report(null, "Generator %s has returned a chunk that is not loaded when requested to generate a chunk at (%d; %d; %d)",
|
throw CrashReports.report(
|
||||||
|
null,
|
||||||
|
"Generator %s has returned a chunk that is not loaded when requested to generate a chunk at (%d; %d; %d)",
|
||||||
getGenerator(),
|
getGenerator(),
|
||||||
chunkPos.x, chunkPos.y, chunkPos.z
|
chunkPos.x,
|
||||||
|
chunkPos.y,
|
||||||
|
chunkPos.z
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!getChunk(chunk).isReady()) {
|
if (!getChunk(chunk).isReady()) {
|
||||||
throw CrashReports.report(null, "Generator %s has returned a chunk that is not ready when requested to generate a chunk at (%d; %d; %d)",
|
throw CrashReports.report(
|
||||||
|
null,
|
||||||
|
"Generator %s has returned a chunk that is not ready when requested to generate a chunk at (%d; %d; %d)",
|
||||||
getGenerator(),
|
getGenerator(),
|
||||||
chunkPos.x, chunkPos.y, chunkPos.z
|
chunkPos.x,
|
||||||
|
chunkPos.y,
|
||||||
|
chunkPos.z
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -21,10 +21,13 @@ import java.util.Collection;
|
|||||||
|
|
||||||
import glm.vec._3.i.Vec3i;
|
import glm.vec._3.i.Vec3i;
|
||||||
import ru.windcorp.progressia.common.world.WorldData;
|
import ru.windcorp.progressia.common.world.WorldData;
|
||||||
|
import ru.windcorp.progressia.common.world.entity.EntityData;
|
||||||
import ru.windcorp.progressia.common.world.rels.BlockFace;
|
import ru.windcorp.progressia.common.world.rels.BlockFace;
|
||||||
|
|
||||||
public interface WorldLogic extends WorldLogicRO {
|
public interface WorldLogic extends WorldLogicRO {
|
||||||
|
|
||||||
|
void spawnEntity(EntityData entity);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Override return types
|
* Override return types
|
||||||
*/
|
*/
|
||||||
|
@ -0,0 +1,75 @@
|
|||||||
|
/*
|
||||||
|
* Progressia
|
||||||
|
* Copyright (C) 2020-2021 Wind Corporation and contributors
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package ru.windcorp.progressia.server.world.tasks;
|
||||||
|
|
||||||
|
import java.util.function.Consumer;
|
||||||
|
|
||||||
|
import glm.vec._3.i.Vec3i;
|
||||||
|
import ru.windcorp.progressia.common.world.entity.EntityData;
|
||||||
|
import ru.windcorp.progressia.server.Server;
|
||||||
|
|
||||||
|
class AddEntity extends CachedChange {
|
||||||
|
|
||||||
|
private EntityData entity;
|
||||||
|
|
||||||
|
public AddEntity(Consumer<? super CachedChange> disposer) {
|
||||||
|
super(disposer);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void set(EntityData entity) {
|
||||||
|
if (this.entity != null)
|
||||||
|
throw new IllegalStateException("Entity is not null. Current: " + this.entity + "; requested: " + entity);
|
||||||
|
|
||||||
|
this.entity = entity;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void affect(Server server) {
|
||||||
|
server.getWorld().spawnEntity(entity);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void getRelevantChunk(Vec3i output) {
|
||||||
|
// Do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isThreadSensitive() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void dispose() {
|
||||||
|
super.dispose();
|
||||||
|
this.entity = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return System.identityHashCode(entity);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object obj) {
|
||||||
|
if (!(obj instanceof AddEntity))
|
||||||
|
return false;
|
||||||
|
return ((AddEntity) obj).entity == entity;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,75 @@
|
|||||||
|
/*
|
||||||
|
* Progressia
|
||||||
|
* Copyright (C) 2020-2021 Wind Corporation and contributors
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package ru.windcorp.progressia.server.world.tasks;
|
||||||
|
|
||||||
|
import java.util.function.Consumer;
|
||||||
|
|
||||||
|
import glm.vec._3.i.Vec3i;
|
||||||
|
import ru.windcorp.progressia.common.world.entity.EntityData;
|
||||||
|
import ru.windcorp.progressia.server.Server;
|
||||||
|
|
||||||
|
class RemoveEntity extends CachedChange {
|
||||||
|
|
||||||
|
private long entityId = EntityData.NULL_ENTITY_ID;
|
||||||
|
|
||||||
|
public RemoveEntity(Consumer<? super CachedChange> disposer) {
|
||||||
|
super(disposer);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void set(long entityId) {
|
||||||
|
if (this.entityId != EntityData.NULL_ENTITY_ID)
|
||||||
|
throw new IllegalStateException("Entity ID is not null. Current: " + this.entityId + "; requested: " + entityId);
|
||||||
|
|
||||||
|
this.entityId = entityId;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void affect(Server server) {
|
||||||
|
server.getWorld().getData().removeEntity(entityId);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void getRelevantChunk(Vec3i output) {
|
||||||
|
// Do nothing
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isThreadSensitive() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void dispose() {
|
||||||
|
super.dispose();
|
||||||
|
this.entityId = EntityData.NULL_ENTITY_ID;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int hashCode() {
|
||||||
|
return Long.hashCode(entityId);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object obj) {
|
||||||
|
if (!(obj instanceof RemoveEntity))
|
||||||
|
return false;
|
||||||
|
return ((RemoveEntity) obj).entityId == entityId;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -46,6 +46,9 @@ public class WorldAccessor implements ReportingServerContext.ChangeListener {
|
|||||||
.addClass(SetBlock.class, () -> new SetBlock(disposer))
|
.addClass(SetBlock.class, () -> new SetBlock(disposer))
|
||||||
.addClass(AddTile.class, () -> new AddTile(disposer))
|
.addClass(AddTile.class, () -> new AddTile(disposer))
|
||||||
.addClass(RemoveTile.class, () -> new RemoveTile(disposer))
|
.addClass(RemoveTile.class, () -> new RemoveTile(disposer))
|
||||||
|
|
||||||
|
.addClass(AddEntity.class, () -> new AddEntity(disposer))
|
||||||
|
.addClass(RemoveEntity.class, () -> new RemoveEntity(disposer))
|
||||||
.addClass(ChangeEntity.class, () -> new ChangeEntity(disposer))
|
.addClass(ChangeEntity.class, () -> new ChangeEntity(disposer))
|
||||||
|
|
||||||
.addClass(BlockTriggeredUpdate.class, () -> new BlockTriggeredUpdate(disposer))
|
.addClass(BlockTriggeredUpdate.class, () -> new BlockTriggeredUpdate(disposer))
|
||||||
@ -81,14 +84,16 @@ public class WorldAccessor implements ReportingServerContext.ChangeListener {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onEntityAdded(EntityData entity) {
|
public void onEntityAdded(EntityData entity) {
|
||||||
// TODO Auto-generated method stub
|
AddEntity change = cache.grab(AddEntity.class);
|
||||||
|
change.set(entity);
|
||||||
|
server.requestChange(change);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onEntityRemoved(long entityId) {
|
public void onEntityRemoved(long entityId) {
|
||||||
// TODO Auto-generated method stub
|
RemoveEntity change = cache.grab(RemoveEntity.class);
|
||||||
|
change.set(entityId);
|
||||||
|
server.requestChange(change);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -266,12 +266,21 @@ public class LayerTestGUI extends GUILayer {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static final String[] CLOCK_CHARS = "\u2591\u2598\u259d\u2580\u2596\u258c\u259e\u259b\u2597\u259a\u2590\u259c\u2584\u2599\u259f\u2588"
|
||||||
|
.chars().mapToObj(c -> ((char) c) + "").toArray(String[]::new);
|
||||||
|
|
||||||
|
private static String getTPSClockChar() {
|
||||||
|
return CLOCK_CHARS[(int) (ServerState.getInstance().getUptimeTicks() % CLOCK_CHARS.length)];
|
||||||
|
}
|
||||||
|
|
||||||
private static final Averager FPS_RECORD = new Averager();
|
private static final Averager FPS_RECORD = new Averager();
|
||||||
private static final Averager TPS_RECORD = new Averager();
|
private static final Averager TPS_RECORD = new Averager();
|
||||||
|
|
||||||
private static final Supplier<CharSequence> TPS_STRING = DynamicStrings.builder()
|
private static final Supplier<CharSequence> TPS_STRING = DynamicStrings.builder()
|
||||||
.addDyn(new MutableStringLocalized("LayerTestGUI.TPSDisplay"))
|
.addDyn(new MutableStringLocalized("LayerTestGUI.TPSDisplay"))
|
||||||
.addDyn(() -> TPS_RECORD.update(ServerState.getInstance().getTPS()), 5, 1)
|
.addDyn(() -> TPS_RECORD.update(ServerState.getInstance().getTPS()), 5, 1)
|
||||||
|
.add(' ')
|
||||||
|
.addDyn(LayerTestGUI::getTPSClockChar)
|
||||||
.buildSupplier();
|
.buildSupplier();
|
||||||
|
|
||||||
private static final Supplier<CharSequence> POS_STRING = DynamicStrings.builder()
|
private static final Supplier<CharSequence> POS_STRING = DynamicStrings.builder()
|
||||||
|
@ -0,0 +1,51 @@
|
|||||||
|
/*
|
||||||
|
* Progressia
|
||||||
|
* Copyright (C) 2020-2021 Wind Corporation and contributors
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
package ru.windcorp.progressia.test;
|
||||||
|
|
||||||
|
import glm.vec._3.Vec3;
|
||||||
|
import glm.vec._3.i.Vec3i;
|
||||||
|
import ru.windcorp.progressia.common.world.block.BlockDataRegistry;
|
||||||
|
import ru.windcorp.progressia.common.world.entity.EntityData;
|
||||||
|
import ru.windcorp.progressia.server.world.block.BlockLogic;
|
||||||
|
import ru.windcorp.progressia.server.world.block.TickableBlock;
|
||||||
|
import ru.windcorp.progressia.server.world.context.ServerBlockContext;
|
||||||
|
import ru.windcorp.progressia.server.world.context.ServerBlockContextRO;
|
||||||
|
import ru.windcorp.progressia.server.world.ticking.TickingPolicy;
|
||||||
|
|
||||||
|
public class TestBlockLogicStatieSpawner extends BlockLogic implements TickableBlock {
|
||||||
|
|
||||||
|
public TestBlockLogicStatieSpawner(String id) {
|
||||||
|
super(id);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void tick(ServerBlockContext context) {
|
||||||
|
Vec3i loc = context.toAbsolute(context.getLocation(), null);
|
||||||
|
EntityData entity = new TestEntityDataStatie();
|
||||||
|
entity.setPosition(new Vec3(loc.x, loc.y, loc.z));
|
||||||
|
|
||||||
|
context.addEntity(entity);
|
||||||
|
context.setBlock(BlockDataRegistry.getInstance().get("Test:Air"));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public TickingPolicy getTickingPolicy(ServerBlockContextRO context) {
|
||||||
|
return TickingPolicy.RANDOM;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -132,6 +132,10 @@ public class TestContent {
|
|||||||
// Sic, using Glass logic for leaves because Test
|
// Sic, using Glass logic for leaves because Test
|
||||||
register(new TestBlockLogicGlass("Test:TemporaryLeaves"));
|
register(new TestBlockLogicGlass("Test:TemporaryLeaves"));
|
||||||
|
|
||||||
|
register(new BlockData("Test:StatieSpawner"));
|
||||||
|
register(new BlockRenderOpaqueCube("Test:StatieSpawner", getBlockTexture("StatieSpawner")));
|
||||||
|
register(new TestBlockLogicStatieSpawner("Test:StatieSpawner"));
|
||||||
|
|
||||||
BlockDataRegistry.getInstance().values().forEach(PLACEABLE_BLOCKS::add);
|
BlockDataRegistry.getInstance().values().forEach(PLACEABLE_BLOCKS::add);
|
||||||
PLACEABLE_BLOCKS.removeIf(b -> placeableBlacklist.contains(b.getId()));
|
PLACEABLE_BLOCKS.removeIf(b -> placeableBlacklist.contains(b.getId()));
|
||||||
PLACEABLE_BLOCKS.sort(Comparator.comparing(BlockData::getId));
|
PLACEABLE_BLOCKS.sort(Comparator.comparing(BlockData::getId));
|
||||||
|
@ -18,26 +18,38 @@
|
|||||||
|
|
||||||
package ru.windcorp.progressia.test;
|
package ru.windcorp.progressia.test;
|
||||||
|
|
||||||
|
import ru.windcorp.progressia.client.graphics.backend.GraphicsInterface;
|
||||||
import ru.windcorp.progressia.client.graphics.model.Renderable;
|
import ru.windcorp.progressia.client.graphics.model.Renderable;
|
||||||
import ru.windcorp.progressia.client.graphics.model.ShapeRenderHelper;
|
import ru.windcorp.progressia.client.graphics.model.ShapeRenderHelper;
|
||||||
import ru.windcorp.progressia.client.graphics.model.Shapes;
|
import ru.windcorp.progressia.client.graphics.model.Shapes.PppBuilder;
|
||||||
import ru.windcorp.progressia.client.graphics.texture.Texture;
|
import ru.windcorp.progressia.client.graphics.texture.ComplexTexture;
|
||||||
|
import ru.windcorp.progressia.client.graphics.texture.TexturePrimitive;
|
||||||
import ru.windcorp.progressia.client.graphics.world.WorldRenderProgram;
|
import ru.windcorp.progressia.client.graphics.world.WorldRenderProgram;
|
||||||
import ru.windcorp.progressia.client.world.entity.EntityRender;
|
import ru.windcorp.progressia.client.world.entity.EntityRender;
|
||||||
|
import ru.windcorp.progressia.client.world.entity.EntityRenderRegistry;
|
||||||
import ru.windcorp.progressia.client.world.entity.EntityRenderable;
|
import ru.windcorp.progressia.client.world.entity.EntityRenderable;
|
||||||
import ru.windcorp.progressia.common.world.entity.EntityData;
|
import ru.windcorp.progressia.common.world.entity.EntityData;
|
||||||
|
|
||||||
public class TestEntityRenderStatie extends EntityRender {
|
public class TestEntityRenderStatie extends EntityRender {
|
||||||
|
|
||||||
private final Renderable cube = new Shapes.PppBuilder(
|
private final static int PARTICLE_COUNT = 16;
|
||||||
WorldRenderProgram.getDefault(),
|
private final Renderable core;
|
||||||
(Texture) null
|
private final Renderable particle;
|
||||||
)
|
|
||||||
.setColorMultiplier(1, 1, 0)
|
|
||||||
.create();
|
|
||||||
|
|
||||||
public TestEntityRenderStatie(String id) {
|
public TestEntityRenderStatie(String id) {
|
||||||
super(id);
|
super(id);
|
||||||
|
|
||||||
|
TexturePrimitive texturePrimitive = EntityRenderRegistry.getEntityTexture("Statie");
|
||||||
|
ComplexTexture texture = new ComplexTexture(texturePrimitive, 4, 4);
|
||||||
|
WorldRenderProgram program = WorldRenderProgram.getDefault();
|
||||||
|
|
||||||
|
final float coreSize = 1f / 4;
|
||||||
|
final float particleSize = 1f / 16;
|
||||||
|
|
||||||
|
core = new PppBuilder(program, texture.getCuboidTextures(0, 2, 1)).setSize(coreSize).centerAt(0, 0, 0).create();
|
||||||
|
particle = new PppBuilder(program, texture.getCuboidTextures(0, 0, 1)).setSize(particleSize)
|
||||||
|
.centerAt(2.5f * coreSize, 0, 0).create();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -45,13 +57,29 @@ public class TestEntityRenderStatie extends EntityRender {
|
|||||||
return new EntityRenderable(entity) {
|
return new EntityRenderable(entity) {
|
||||||
@Override
|
@Override
|
||||||
public void doRender(ShapeRenderHelper renderer) {
|
public void doRender(ShapeRenderHelper renderer) {
|
||||||
|
double phase = GraphicsInterface.getTime();
|
||||||
|
renderer.pushTransform().translate(0, 0, (float) Math.sin(phase) * 0.1f);
|
||||||
|
|
||||||
renderer.pushTransform().scale(
|
renderer.pushTransform().scale(
|
||||||
((TestEntityDataStatie) entity).getSize() / 24.0f
|
((TestEntityDataStatie) entity).getSize() / 24.0f
|
||||||
);
|
).rotateY((float) -Math.sin(phase - Math.PI / 3) * Math.PI / 12);
|
||||||
|
|
||||||
cube.render(renderer);
|
core.render(renderer);
|
||||||
|
|
||||||
renderer.popTransform();
|
renderer.popTransform();
|
||||||
|
renderer.popTransform();
|
||||||
|
renderer.pushTransform().translate(0, 0, (float) Math.sin(phase + Math.PI / 2) * 0.05f);
|
||||||
|
|
||||||
|
for (int i = 0; i < PARTICLE_COUNT; ++i) {
|
||||||
|
double phaseOffset = 2 * Math.PI / PARTICLE_COUNT * i;
|
||||||
|
renderer.pushTransform()
|
||||||
|
.translate((float) Math.sin(phase + phaseOffset) * 0.1f, 0, 0)
|
||||||
|
.rotateX(Math.sin(phase / 2 + phaseOffset) * Math.PI / 6)
|
||||||
|
.rotateZ(phase + phaseOffset * 2);
|
||||||
|
particle.render(renderer);
|
||||||
|
renderer.popTransform();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
BIN
src/main/resources/assets/textures/blocks/StatieSpawner.png
Normal file
BIN
src/main/resources/assets/textures/blocks/StatieSpawner.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.5 KiB |
BIN
src/main/resources/assets/textures/entities/Statie.png
Normal file
BIN
src/main/resources/assets/textures/entities/Statie.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.3 KiB |
Binary file not shown.
Before Width: | Height: | Size: 1.9 KiB After Width: | Height: | Size: 11 KiB |
Reference in New Issue
Block a user