diff --git a/src/main/java/de/welterde/em/Entity.java b/src/main/java/de/welterde/em/Entity.java
index 09d62c3..04651d0 100644
--- a/src/main/java/de/welterde/em/Entity.java
+++ b/src/main/java/de/welterde/em/Entity.java
@@ -21,6 +21,7 @@ package de.welterde.em;
* @author welterde
*/
public interface Entity {
+ public GameContext getContext();
public int getEntityId();
- public void initEntity(EntityStorage ctx, int id);
+ public void initEntity(GameContext ctx, int id);
}
diff --git a/src/main/java/de/welterde/em/EntityBase.java b/src/main/java/de/welterde/em/EntityBase.java
index 7b41bf4..c649408 100644
--- a/src/main/java/de/welterde/em/EntityBase.java
+++ b/src/main/java/de/welterde/em/EntityBase.java
@@ -23,7 +23,7 @@ import de.welterde.em.io.EntityRecord;
* @author welterde
*/
public abstract class EntityBase implements Entity {
- protected EntityStorage ctx;
+ protected GameContext ctx;
protected int id;
public EntityBase() {
@@ -31,7 +31,7 @@ public abstract class EntityBase implements Entity {
this.ctx = null;
}
- public EntityBase(EntityStorage ctx, int id) {
+ public EntityBase(GameContext ctx, int id) {
this.id = id;
this.ctx = ctx;
}
@@ -41,12 +41,14 @@ public abstract class EntityBase implements Entity {
this.ctx = r.getContext();
}
+ @Override
public int getEntityId() {
if(this.id == -1)
throw new IllegalStateException("Entity not initialized");
return this.id;
}
- public void initEntity(EntityStorage ctx, int id) {
+ @Override
+ public void initEntity(GameContext ctx, int id) {
if((this.id != -1) && (this.ctx != null))
throw new IllegalStateException("Entity already initialized");
if(id == -1)
@@ -61,4 +63,11 @@ public abstract class EntityBase implements Entity {
return this.id != -1;
}
+ @Override
+ public GameContext getContext() {
+ if(this.ctx == null)
+ throw new IllegalStateException("Entity not initialized");
+ return this.ctx;
+ }
+
}
diff --git a/src/main/java/de/welterde/em/EntityContainer.java b/src/main/java/de/welterde/em/EntityContainer.java
new file mode 100644
index 0000000..8652f07
--- /dev/null
+++ b/src/main/java/de/welterde/em/EntityContainer.java
@@ -0,0 +1,27 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em;
+
+/**
+ *
+ * @author welterde
+ */
+public interface EntityContainer {
+ public void addEntity(Entity e);
+ public Iterable listEntities();
+ public void removeEntity(Entity e);
+}
diff --git a/src/main/java/de/welterde/em/EntityRef.java b/src/main/java/de/welterde/em/EntityRef.java
index 16d050f..1a76616 100644
--- a/src/main/java/de/welterde/em/EntityRef.java
+++ b/src/main/java/de/welterde/em/EntityRef.java
@@ -28,18 +28,24 @@ public class EntityRef {
static Location maybeGet(EntityRef currentLocation) {
throw new UnsupportedOperationException("Not supported yet."); // Generated from nbfs://nbhost/SystemFileSystem/Templates/Classes/Code/GeneratedMethodBody
}
- protected final EntityStorage ctx;
+ protected final GameContext ctx;
protected WeakReference ref;
protected final int entityId;
protected boolean invalid;
- public EntityRef(EntityStorage ctx, X entity) {
+ public EntityRef(GameContext ctx, X entity) {
this.ctx = ctx;
this.entityId = entity.getEntityId();
this.invalid = false;
}
+ public EntityRef(X entity) {
+ this.ctx = entity.getContext();
+ this.entityId = entity.getEntityId();
+ this.invalid = false;
+ }
+
public X get() {
if(this.invalid)
throw new InvalidEntityReference(this.entityId);
@@ -68,4 +74,5 @@ public class EntityRef {
}
}
}
+
}
diff --git a/src/main/java/de/welterde/em/GameContext.java b/src/main/java/de/welterde/em/GameContext.java
new file mode 100644
index 0000000..2615ffc
--- /dev/null
+++ b/src/main/java/de/welterde/em/GameContext.java
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em;
+
+import de.welterde.em.data.CounterName;
+
+/**
+ *
+ * @author welterde
+ */
+public interface GameContext {
+ public Entity getEntity(int entityId);
+
+ public EntityContainer getContainer(int entityId);
+
+ int allocateId(CounterName name);
+
+ int addEntity(EntityBase e);
+}
diff --git a/src/main/java/de/welterde/em/LocatedEntity.java b/src/main/java/de/welterde/em/LocatedEntity.java
index a2a1ee0..d823ac1 100644
--- a/src/main/java/de/welterde/em/LocatedEntity.java
+++ b/src/main/java/de/welterde/em/LocatedEntity.java
@@ -20,13 +20,7 @@ package de.welterde.em;
*
* @author welterde
*/
-public class LocatedEntity extends EntityBase {
- protected EntityRef currentLocation;
-
- public Location getLocation() {
- if(this.currentLocation == null)
- return null;
- else
- return this.currentLocation.get();
- }
+public interface LocatedEntity extends Entity {
+ public Location getLocation();
+ public void setLocation(Location newLoc);
}
diff --git a/src/main/java/de/welterde/em/LocatedEntityBase.java b/src/main/java/de/welterde/em/LocatedEntityBase.java
new file mode 100644
index 0000000..a68e8a5
--- /dev/null
+++ b/src/main/java/de/welterde/em/LocatedEntityBase.java
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em;
+
+/**
+ *
+ * @author welterde
+ */
+public class LocatedEntityBase extends EntityBase implements LocatedEntity {
+ protected EntityRef currentLocation;
+
+ @Override
+ public Location getLocation() {
+ if(this.currentLocation == null)
+ return null;
+ else
+ return this.currentLocation.get();
+ }
+
+ @Override
+ public void setLocation(Location newLoc) {
+ newLoc.addEntity(this);
+ if(this.currentLocation != null) {
+ this.currentLocation.get().removeEntity(this);
+ }
+ this.currentLocation = new EntityRef(newLoc);
+ }
+}
diff --git a/src/main/java/de/welterde/em/Location.java b/src/main/java/de/welterde/em/Location.java
index 44add0d..5cb231f 100644
--- a/src/main/java/de/welterde/em/Location.java
+++ b/src/main/java/de/welterde/em/Location.java
@@ -16,11 +16,18 @@
*/
package de.welterde.em;
+import de.welterde.em.w.Area;
+
/**
*
* @author welterde
*/
-public interface Location extends Entity {
+public interface Location extends Entity, EntityContainer {
public short getSecurityLevel();
public Location setSecurityLevel(short newLevel);
+
+ public Area getArea();
+ public void setArea(Area area);
+
+
}
diff --git a/src/main/java/de/welterde/em/EntityStorage.java b/src/main/java/de/welterde/em/LocationListener.java
similarity index 90%
rename from src/main/java/de/welterde/em/EntityStorage.java
rename to src/main/java/de/welterde/em/LocationListener.java
index d75586d..73cc3bc 100644
--- a/src/main/java/de/welterde/em/EntityStorage.java
+++ b/src/main/java/de/welterde/em/LocationListener.java
@@ -20,6 +20,6 @@ package de.welterde.em;
*
* @author welterde
*/
-public interface EntityStorage {
- public EntityBase getEntity(int entityId);
+public interface LocationListener {
+
}
diff --git a/src/main/java/de/welterde/em/MovableEntity.java b/src/main/java/de/welterde/em/MovableEntity.java
new file mode 100644
index 0000000..a04b46d
--- /dev/null
+++ b/src/main/java/de/welterde/em/MovableEntity.java
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em;
+
+/**
+ *
+ * @author welterde
+ */
+public interface MovableEntity extends Entity, Positioned, LocatedEntity {
+
+}
diff --git a/src/main/java/de/welterde/em/PositionTracker.java b/src/main/java/de/welterde/em/PositionTracker.java
index 71ac737..67dbf2c 100644
--- a/src/main/java/de/welterde/em/PositionTracker.java
+++ b/src/main/java/de/welterde/em/PositionTracker.java
@@ -36,5 +36,5 @@ public interface PositionTracker {
public void moveEntityCardinal(Entity e, Direction dir);
- public void enrollEntity(Entity e, MapCoord startCoord);
+ public void enrollEntity(LocatedEntity e, MapCoord startCoord);
}
diff --git a/src/main/java/de/welterde/em/PositionTrackerImpl.java b/src/main/java/de/welterde/em/PositionTrackerImpl.java
index f802b57..abf49ba 100644
--- a/src/main/java/de/welterde/em/PositionTrackerImpl.java
+++ b/src/main/java/de/welterde/em/PositionTrackerImpl.java
@@ -16,17 +16,50 @@
*/
package de.welterde.em;
+import de.welterde.em.data.Direction;
import de.welterde.em.data.MapCoord;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
/**
*
* @author welterde
*/
-public class PositionTrackerImpl implements PositionTracker {
-
- @Override
- public MapCoord getPosition(Entity e) {
- throw new UnsupportedOperationException("Not supported yet."); // Generated from nbfs://nbhost/SystemFileSystem/Templates/Classes/Code/GeneratedMethodBody
+public class PositionTrackerImpl implements PositionTracker, LocationListener {
+ protected Map map;
+ protected MapCoord coordCenter;
+ protected Map entityCoord;
+
+ public PositionTrackerImpl(Map map, MapCoord coordCenter) {
+ this.map = map;
+ this.coordCenter = coordCenter;
+ this.entityCoord = new ConcurrentHashMap<>();
}
+ @Override
+ public MapCoord getPosition(Entity e) {
+ var eid = e.getEntityId();
+ if(!this.entityCoord.containsKey(eid))
+ return null;
+ var c = this.entityCoord.get(eid);
+ return this.coordCenter.add(c);
+ }
+
+ @Override
+ public void teleportEntity(Entity e, MapCoord destination) {
+ throw new UnsupportedOperationException("Not supported yet."); // Generated from nbfs://nbhost/SystemFileSystem/Templates/Classes/Code/GeneratedMethodBody
+ }
+
+ @Override
+ public void moveEntityCardinal(Entity e, Direction dir) {
+ throw new UnsupportedOperationException("Not supported yet."); // Generated from nbfs://nbhost/SystemFileSystem/Templates/Classes/Code/GeneratedMethodBody
+ }
+
+ @Override
+ public void enrollEntity(LocatedEntity e, MapCoord startCoord) {
+ this.entityCoord.put(e.getEntityId(), startCoord);
+ }
+
+
}
diff --git a/src/main/java/de/welterde/em/Positioned.java b/src/main/java/de/welterde/em/Positioned.java
index b8f4f36..42da9a5 100644
--- a/src/main/java/de/welterde/em/Positioned.java
+++ b/src/main/java/de/welterde/em/Positioned.java
@@ -20,7 +20,7 @@ package de.welterde.em;
*
* @author welterde
*/
-public interface Positioned {
+public interface Positioned extends LocatedEntity {
public PositionTracker getPositionTracker();
- public void setPositionTracker();
+ public void setPositionTracker(PositionTracker newTracker);
}
diff --git a/src/main/java/de/welterde/em/data/LocationBase.java b/src/main/java/de/welterde/em/PositionedEntityBase.java
similarity index 68%
rename from src/main/java/de/welterde/em/data/LocationBase.java
rename to src/main/java/de/welterde/em/PositionedEntityBase.java
index ad056ad..556dc68 100644
--- a/src/main/java/de/welterde/em/data/LocationBase.java
+++ b/src/main/java/de/welterde/em/PositionedEntityBase.java
@@ -14,26 +14,24 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-package de.welterde.em.data;
-
-import de.welterde.em.Location;
+package de.welterde.em;
/**
*
* @author welterde
*/
-public abstract class LocationBase implements Location {
+public class PositionedEntityBase extends LocatedEntityBase implements Positioned {
- protected short securityLevel;
+ protected PositionTracker positionTracker;
@Override
- public short getSecurityLevel() {
- return this.securityLevel;
+ public PositionTracker getPositionTracker() {
+ return this.positionTracker;
+ }
+
+ @Override
+ public void setPositionTracker(PositionTracker newTracker) {
+ this.positionTracker = newTracker;
}
- @Override
- public Location setSecurityLevel(short newLevel) {
- this.securityLevel = newLevel;
- return this;
- }
}
diff --git a/src/main/java/de/welterde/em/data/Tile.java b/src/main/java/de/welterde/em/Tile.java
similarity index 90%
rename from src/main/java/de/welterde/em/data/Tile.java
rename to src/main/java/de/welterde/em/Tile.java
index 0dcf655..865f130 100644
--- a/src/main/java/de/welterde/em/data/Tile.java
+++ b/src/main/java/de/welterde/em/Tile.java
@@ -14,9 +14,12 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-package de.welterde.em.data;
+package de.welterde.em;
import de.welterde.em.Location;
+import de.welterde.em.data.Direction;
+import de.welterde.em.data.Entity;
+import de.welterde.em.data.TileType;
/**
*
diff --git a/src/main/java/de/welterde/em/TileMap.java b/src/main/java/de/welterde/em/TileMap.java
new file mode 100644
index 0000000..d0967cf
--- /dev/null
+++ b/src/main/java/de/welterde/em/TileMap.java
@@ -0,0 +1,27 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em;
+
+import de.welterde.em.data.MapCoord;
+
+/**
+ *
+ * @author welterde
+ */
+public interface TileMap {
+ public Tile getTile(MapCoord c);
+}
diff --git a/src/main/java/de/welterde/em/data/BasicEntityCollection.java b/src/main/java/de/welterde/em/data/BasicEntityCollection.java
new file mode 100644
index 0000000..b38ed2e
--- /dev/null
+++ b/src/main/java/de/welterde/em/data/BasicEntityCollection.java
@@ -0,0 +1,102 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em.data;
+
+import de.welterde.em.EntityContainer;
+import java.util.Arrays;
+import java.util.Set;
+import java.util.TreeSet;
+import java.util.concurrent.BlockingQueue;
+import java.util.concurrent.LinkedBlockingDeque;
+import java.util.concurrent.locks.ReadWriteLock;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+import de.welterde.em.GameContext;
+
+/**
+ *
+ * @author welterde
+ */
+public class BasicEntityCollection implements EntityContainer {
+ protected final GameContext ctx;
+ protected Set entities;
+ protected final ReadWriteLock structLock;
+ protected Thread houseKeepingThread;
+
+ protected BlockingQueue taskQ;
+
+ public BasicEntityCollection(GameContext ctx) {
+ this.ctx = ctx;
+ this.entities = new TreeSet<>();
+ this.structLock = new ReentrantReadWriteLock();
+ this.taskQ = new LinkedBlockingDeque<>();
+
+ this.houseKeepingThread = Thread
+ .ofVirtual()
+ .name("entitycollection")
+ .start(() -> this.housekeep());
+ }
+
+ @Override
+ public void addEntity(de.welterde.em.Entity e) {
+ this.taskQ.add(new Task(e.getEntityId(), false));
+ }
+ @Override
+ public Iterable listEntities() {
+ this.structLock.readLock().lock();
+ try {
+ // create copy of the entity list so we can hand out the iterator
+ final Integer[] ids = new Integer[this.entities.size()];
+ this.entities.toArray(ids);
+
+ final Iterable i = () -> Arrays.stream(ids).map(eid -> (de.welterde.em.Entity) this.ctx.getEntity(eid)).iterator();
+ return i;
+ } finally {
+ this.structLock.readLock().unlock();
+ }
+ }
+ @Override
+ public void removeEntity(de.welterde.em.Entity e) {
+ this.taskQ.add(new Task(e.getEntityId(), true));
+ }
+
+ protected void housekeep() {
+ while(true) {
+ Task task;
+ try {
+ task = this.taskQ.take();
+ } catch (InterruptedException ex) {
+ System.getLogger(BasicEntityCollection.class.getName()).log(System.Logger.Level.ERROR, (String) null, ex);
+ continue;
+ }
+
+ this.structLock.writeLock().lock();
+ try {
+ if(task.remove()) {
+ this.entities.remove(task.eid());
+ } else {
+ this.entities.add(task.eid());
+ }
+ } finally {
+ this.structLock.writeLock().unlock();
+ }
+ }
+ }
+
+ record Task(Integer eid, boolean remove) {
+
+ }
+}
diff --git a/src/main/java/de/welterde/em/data/EntityPosMgr.java b/src/main/java/de/welterde/em/data/EntityPosMgr.java
index 62839e4..160e629 100644
--- a/src/main/java/de/welterde/em/data/EntityPosMgr.java
+++ b/src/main/java/de/welterde/em/data/EntityPosMgr.java
@@ -16,6 +16,8 @@
*/
package de.welterde.em.data;
+import de.welterde.em.Tile;
+
/**
* Manages position and occupied tiles by entities
*
diff --git a/src/main/java/de/welterde/em/data/LocationManager.java b/src/main/java/de/welterde/em/data/LocationManager.java
index 0e649b8..2b0645f 100644
--- a/src/main/java/de/welterde/em/data/LocationManager.java
+++ b/src/main/java/de/welterde/em/data/LocationManager.java
@@ -16,6 +16,8 @@
*/
package de.welterde.em.data;
+import de.welterde.em.loc.Corridor;
+
/**
* Manages locations like rooms, corridors, sectors
* @author welterde
diff --git a/src/main/java/de/welterde/em/data/MapCoord.java b/src/main/java/de/welterde/em/data/MapCoord.java
index feca9f5..1010e2f 100644
--- a/src/main/java/de/welterde/em/data/MapCoord.java
+++ b/src/main/java/de/welterde/em/data/MapCoord.java
@@ -44,4 +44,8 @@ public record MapCoord(int z, int x, int y) {
public MapCoord add(CoordVector v) {
return new MapCoord(z + v.dz(), x + v.dx(), y + v.dy());
}
+
+ public MapCoord add(MapCoord c) {
+ return new MapCoord(this.z + c.z(), this.x + c.x(), this.y + c.y());
+ }
}
diff --git a/src/main/java/de/welterde/em/data/OutpostMap.java b/src/main/java/de/welterde/em/data/OutpostMap.java
index 8c4fcb2..a9e3605 100644
--- a/src/main/java/de/welterde/em/data/OutpostMap.java
+++ b/src/main/java/de/welterde/em/data/OutpostMap.java
@@ -4,6 +4,7 @@
*/
package de.welterde.em.data;
+import de.welterde.em.Tile;
import de.welterde.em.Location;
import java.util.EnumMap;
import java.util.HashMap;
diff --git a/src/main/java/de/welterde/em/data/TerrainGen.java b/src/main/java/de/welterde/em/data/TerrainGen.java
index a8dbefa..41beaae 100644
--- a/src/main/java/de/welterde/em/data/TerrainGen.java
+++ b/src/main/java/de/welterde/em/data/TerrainGen.java
@@ -16,6 +16,8 @@
*/
package de.welterde.em.data;
+import de.welterde.em.Tile;
+
/**
*
* @author welterde
diff --git a/src/main/java/de/welterde/em/data/TileImpl.java b/src/main/java/de/welterde/em/data/TileImpl.java
index 05a52d0..f12b8a2 100644
--- a/src/main/java/de/welterde/em/data/TileImpl.java
+++ b/src/main/java/de/welterde/em/data/TileImpl.java
@@ -16,6 +16,7 @@
*/
package de.welterde.em.data;
+import de.welterde.em.Tile;
import de.welterde.em.Location;
import de.welterde.em.CollisionException;
diff --git a/src/main/java/de/welterde/em/data/gen/BasicTerrainGen.java b/src/main/java/de/welterde/em/data/gen/BasicTerrainGen.java
index f788c9e..da0e2d8 100644
--- a/src/main/java/de/welterde/em/data/gen/BasicTerrainGen.java
+++ b/src/main/java/de/welterde/em/data/gen/BasicTerrainGen.java
@@ -19,7 +19,7 @@ package de.welterde.em.data.gen;
import de.welterde.em.data.MapCoord;
import de.welterde.em.data.OutpostMap;
import de.welterde.em.data.TerrainGen;
-import de.welterde.em.data.Tile;
+import de.welterde.em.Tile;
import de.welterde.em.data.TileImpl;
import de.welterde.em.data.TileType;
diff --git a/src/main/java/de/welterde/em/e/Employee.java b/src/main/java/de/welterde/em/e/Employee.java
index 35b1b97..ef92210 100644
--- a/src/main/java/de/welterde/em/e/Employee.java
+++ b/src/main/java/de/welterde/em/e/Employee.java
@@ -19,13 +19,14 @@ package de.welterde.em.e;
import de.welterde.em.EntityBase;
import de.welterde.em.EntityRef;
import de.welterde.em.Location;
+import de.welterde.em.PositionedEntityBase;
import de.welterde.em.w.Org;
/**
*
* @author welterde
*/
-public class Employee extends EntityBase {
+public class Employee extends PositionedEntityBase {
protected String name;
protected EntityRef employer;
diff --git a/src/main/java/de/welterde/em/entity/ItemBase.java b/src/main/java/de/welterde/em/entity/ItemBase.java
index a5f14fe..c677605 100644
--- a/src/main/java/de/welterde/em/entity/ItemBase.java
+++ b/src/main/java/de/welterde/em/entity/ItemBase.java
@@ -17,7 +17,7 @@
package de.welterde.em.entity;
import de.welterde.em.EntityBase;
-import de.welterde.em.EntityStorage;
+import de.welterde.em.GameContext;
/**
*
@@ -25,7 +25,7 @@ import de.welterde.em.EntityStorage;
*/
public abstract class ItemBase extends EntityBase {
- public ItemBase(EntityStorage ctx, int id) {
+ public ItemBase(GameContext ctx, int id) {
super(ctx, id);
}
}
diff --git a/src/main/java/de/welterde/em/io/EntityRecord.java b/src/main/java/de/welterde/em/io/EntityRecord.java
index 8f54d17..47cf683 100644
--- a/src/main/java/de/welterde/em/io/EntityRecord.java
+++ b/src/main/java/de/welterde/em/io/EntityRecord.java
@@ -16,7 +16,7 @@
*/
package de.welterde.em.io;
-import de.welterde.em.EntityStorage;
+import de.welterde.em.GameContext;
/**
*
@@ -24,5 +24,5 @@ import de.welterde.em.EntityStorage;
*/
public interface EntityRecord {
public int getID();
- public EntityStorage getContext();
+ public GameContext getContext();
}
diff --git a/src/main/java/de/welterde/em/data/Corridor.java b/src/main/java/de/welterde/em/loc/Corridor.java
similarity index 92%
rename from src/main/java/de/welterde/em/data/Corridor.java
rename to src/main/java/de/welterde/em/loc/Corridor.java
index 259c6e7..2de9500 100644
--- a/src/main/java/de/welterde/em/data/Corridor.java
+++ b/src/main/java/de/welterde/em/loc/Corridor.java
@@ -14,8 +14,9 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-package de.welterde.em.data;
+package de.welterde.em.loc;
+import de.welterde.em.loc.LocationBase;
import de.welterde.em.Location;
/**
diff --git a/src/main/java/de/welterde/em/loc/LocationBase.java b/src/main/java/de/welterde/em/loc/LocationBase.java
new file mode 100644
index 0000000..4c6311e
--- /dev/null
+++ b/src/main/java/de/welterde/em/loc/LocationBase.java
@@ -0,0 +1,86 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em.loc;
+
+import de.welterde.em.Entity;
+import de.welterde.em.EntityBase;
+import de.welterde.em.EntityContainer;
+import de.welterde.em.Location;
+import de.welterde.em.data.BasicEntityCollection;
+import de.welterde.em.w.Area;
+import java.util.concurrent.locks.ReadWriteLock;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+import de.welterde.em.GameContext;
+
+/**
+ *
+ * @author welterde
+ */
+public abstract class LocationBase extends EntityBase implements Location {
+
+ protected short securityLevel;
+ protected Area area;
+ protected final ReadWriteLock structLock;
+ protected EntityContainer entityContainer;
+
+ public LocationBase() {
+ this.structLock = new ReentrantReadWriteLock();
+
+ }
+
+ @Override
+ public short getSecurityLevel() {
+ return this.securityLevel;
+ }
+
+ @Override
+ public Location setSecurityLevel(short newLevel) {
+ this.securityLevel = newLevel;
+ return this;
+ }
+
+ @Override
+ public Area getArea() {
+ return this.area;
+ }
+ @Override
+ public void setArea(Area area) {
+ this.area = area;
+ }
+
+ @Override
+ public void initEntity(GameContext ctx, int id) {
+ super.initEntity(ctx, id);
+ this.entityContainer = new BasicEntityCollection(ctx);
+ }
+
+ @Override
+ public void addEntity(Entity e) {
+ entityContainer.addEntity(e);
+ }
+
+ @Override
+ public Iterable listEntities() {
+ return entityContainer.listEntities();
+ }
+
+ @Override
+ public void removeEntity(Entity e) {
+ entityContainer.removeEntity(e);
+ }
+
+}
diff --git a/src/main/java/de/welterde/em/data/Room.java b/src/main/java/de/welterde/em/loc/Room.java
similarity index 92%
rename from src/main/java/de/welterde/em/data/Room.java
rename to src/main/java/de/welterde/em/loc/Room.java
index 1ff20df..7cd24f9 100644
--- a/src/main/java/de/welterde/em/data/Room.java
+++ b/src/main/java/de/welterde/em/loc/Room.java
@@ -14,8 +14,9 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-package de.welterde.em.data;
+package de.welterde.em.loc;
+import de.welterde.em.loc.LocationBase;
import de.welterde.em.Location;
/**
diff --git a/src/main/java/de/welterde/em/room/RoomType.java b/src/main/java/de/welterde/em/loc/RoomType.java
similarity index 95%
rename from src/main/java/de/welterde/em/room/RoomType.java
rename to src/main/java/de/welterde/em/loc/RoomType.java
index 5dde24f..a423698 100644
--- a/src/main/java/de/welterde/em/room/RoomType.java
+++ b/src/main/java/de/welterde/em/loc/RoomType.java
@@ -14,7 +14,7 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-package de.welterde.em.room;
+package de.welterde.em.loc;
/**
*
@@ -24,4 +24,5 @@ public enum RoomType {
LAB,
OFFICE,
COMPUTER_ROOM,
+ LIBRARY,
}
diff --git a/src/main/java/de/welterde/em/w/Area.java b/src/main/java/de/welterde/em/w/Area.java
index 1c8f557..4d8ba27 100644
--- a/src/main/java/de/welterde/em/w/Area.java
+++ b/src/main/java/de/welterde/em/w/Area.java
@@ -17,29 +17,38 @@
package de.welterde.em.w;
import de.welterde.em.EntityBase;
-import de.welterde.em.EntityStorage;
import de.welterde.em.Location;
+import de.welterde.em.Tile;
+import de.welterde.em.TileMap;
+import de.welterde.em.data.MapCoord;
import de.welterde.em.data.TerrainGen;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.locks.ReadWriteLock;
import java.util.concurrent.locks.ReentrantReadWriteLock;
+import de.welterde.em.GameContext;
/**
*
* @author welterde
*/
-public class Area extends EntityBase {
+public class Area extends EntityBase implements TileMap {
protected final ReadWriteLock structLock;
protected final AreaMap map;
protected final Map locations;
- public Area(EntityStorage ctx, int id, TerrainGen gen) {
- super(ctx, id);
+ public Area(AreaSetup setup) {
this.structLock = new ReentrantReadWriteLock();
this.map = new AreaMap(gen);
this.locations = new HashMap<>();
}
+
+ @Override
+ public Tile getTile(MapCoord c) {
+ return map.getTile(c);
+ }
+
+
}
diff --git a/src/main/java/de/welterde/em/w/AreaMap.java b/src/main/java/de/welterde/em/w/AreaMap.java
index 5dad232..d4f63fb 100644
--- a/src/main/java/de/welterde/em/w/AreaMap.java
+++ b/src/main/java/de/welterde/em/w/AreaMap.java
@@ -16,6 +16,8 @@
*/
package de.welterde.em.w;
+import de.welterde.em.Tile;
+import de.welterde.em.TileMap;
import de.welterde.em.data.MapCoord;
import de.welterde.em.data.TerrainGen;
import java.util.HashMap;
@@ -27,7 +29,7 @@ import java.util.concurrent.locks.ReentrantReadWriteLock;
*
* @author welterde
*/
-public class AreaMap {
+public class AreaMap implements TileMap {
protected final Map blockMap;
protected final TerrainGen gen;
protected final ReadWriteLock structLock;
@@ -46,4 +48,11 @@ public class AreaMap {
return this.tiles.get(c);
}
}
+
+ @Override
+ public Tile getTile(MapCoord c) {
+ throw new UnsupportedOperationException("Not supported yet."); // Generated from nbfs://nbhost/SystemFileSystem/Templates/Classes/Code/GeneratedMethodBody
+ }
+
+
}
diff --git a/src/main/java/de/welterde/em/w/AreaSetup.java b/src/main/java/de/welterde/em/w/AreaSetup.java
new file mode 100644
index 0000000..99726b7
--- /dev/null
+++ b/src/main/java/de/welterde/em/w/AreaSetup.java
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2026 welterde
+ *
+ * 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 .
+ */
+package de.welterde.em.w;
+
+/**
+ *
+ * @author welterde
+ */
+public class AreaSetup {
+
+}
diff --git a/src/main/java/de/welterde/em/w/City.java b/src/main/java/de/welterde/em/w/City.java
index 27e499e..4bd0be0 100644
--- a/src/main/java/de/welterde/em/w/City.java
+++ b/src/main/java/de/welterde/em/w/City.java
@@ -17,14 +17,14 @@
package de.welterde.em.w;
import de.welterde.em.EntityBase;
-import de.welterde.em.EntityStorage;
+import de.welterde.em.GameContext;
/**
*
* @author welterde
*/
public class City extends EntityBase {
- public City(EntityStorage ctx, int id) {
+ public City(GameContext ctx, int id) {
super(ctx, id);
}
}
diff --git a/src/main/java/de/welterde/em/w/Country.java b/src/main/java/de/welterde/em/w/Country.java
index 5a409b5..99aa973 100644
--- a/src/main/java/de/welterde/em/w/Country.java
+++ b/src/main/java/de/welterde/em/w/Country.java
@@ -17,7 +17,7 @@
package de.welterde.em.w;
import de.welterde.em.EntityBase;
-import de.welterde.em.EntityStorage;
+import de.welterde.em.GameContext;
/**
*
@@ -25,7 +25,7 @@ import de.welterde.em.EntityStorage;
*/
public class Country extends EntityBase {
- public Country(EntityStorage ctx, int id) {
+ public Country(GameContext ctx, int id) {
super(ctx, id);
}
diff --git a/src/main/java/de/welterde/em/w/Dimension.java b/src/main/java/de/welterde/em/w/Dimension.java
index 978d6d7..d4baae6 100644
--- a/src/main/java/de/welterde/em/w/Dimension.java
+++ b/src/main/java/de/welterde/em/w/Dimension.java
@@ -40,12 +40,12 @@ public class Dimension extends EntityBase {
this.areas = new HashMap<>();
}
- public Area addArea(TerrainGen gen) {
+ public Area createArea(AreaSetup setup) {
this.structLock.writeLock().lock();
try {
- var areaId = this.ctx.allocateId(CounterName.AREA_IDX);
- var area = new Area(areaId, gen);
- this.areas.put(areaId, area);
+ var area = new Area(setup);
+ var aid = this.ctx.addEntity(area);
+ this.areas.put(aid, area);
return area;
} finally {
this.structLock.writeLock().unlock();
diff --git a/src/main/java/de/welterde/em/w/Outpost.java b/src/main/java/de/welterde/em/w/Outpost.java
index c77ff55..42d6801 100644
--- a/src/main/java/de/welterde/em/w/Outpost.java
+++ b/src/main/java/de/welterde/em/w/Outpost.java
@@ -18,8 +18,8 @@ package de.welterde.em.w;
import de.welterde.em.EntityBase;
import de.welterde.em.EntityRef;
-import de.welterde.em.EntityStorage;
import java.util.EnumSet;
+import de.welterde.em.GameContext;
/**
*
@@ -30,7 +30,7 @@ public class Outpost extends EntityBase {
protected final OutpostLocationType locationType;
protected EntityRef city;
- public Outpost(EntityStorage ctx, int id, OutpostLocationType locationType) {
+ public Outpost(GameContext ctx, int id, OutpostLocationType locationType) {
super(ctx, id);
this.flags = EnumSet.noneOf(OutpostFlags.class);
this.locationType = locationType;
diff --git a/src/main/java/de/welterde/em/w/World.java b/src/main/java/de/welterde/em/w/World.java
index 0a0a349..350f53c 100644
--- a/src/main/java/de/welterde/em/w/World.java
+++ b/src/main/java/de/welterde/em/w/World.java
@@ -16,9 +16,10 @@
*/
package de.welterde.em.w;
+import de.welterde.em.Entity;
import de.welterde.em.EntityBase;
+import de.welterde.em.EntityContainer;
import de.welterde.em.EntityRef;
-import de.welterde.em.EntityStorage;
import de.welterde.em.data.CounterName;
import java.util.ArrayList;
import java.util.EnumMap;
@@ -28,15 +29,19 @@ import java.util.Map;
import java.util.concurrent.atomic.AtomicReference;
import java.util.concurrent.locks.ReadWriteLock;
import java.util.concurrent.locks.ReentrantReadWriteLock;
+import de.welterde.em.GameContext;
/**
*
* @author welterde
*/
-public class World implements EntityStorage {
- protected final ArrayList entities;
+public class World implements GameContext {
+ // base backing storage of entities and entity components
+ protected final ArrayList entities;
+ protected final Map entityContainers;
protected final EnumMap counters;
+ // direct ref to certain top-level entities
protected final ArrayList dimensions;
protected final Map countries;
protected final Map orgs;
@@ -46,10 +51,13 @@ public class World implements EntityStorage {
protected final AtomicReference state;
public World() {
+ this.entities = new ArrayList<>();
+ this.entityContainers = new HashMap<>();
this.counters = new EnumMap<>(CounterName.class);
+
this.dimensions = new ArrayList<>();
this.countries = new HashMap<>();
- this.entities = new ArrayList<>();
+
this.orgs = new HashMap<>();
this.outposts = new HashMap<>();
@@ -58,6 +66,7 @@ public class World implements EntityStorage {
}
+ @Override
public int allocateId(CounterName name) {
synchronized(this.counters) {
// start counter at zero if not yet a thing
@@ -90,12 +99,16 @@ public class World implements EntityStorage {
}
@Override
- public EntityBase getEntity(int entityId) {
+ public Entity getEntity(int entityId) {
return this.entities.get(entityId);
}
+ @Override
+ public EntityContainer getContainer(int entityId) {
+ return this.entityContainers.getOrDefault(entityId, null);
+ }
-
- public void addEntity(EntityBase e) {
+ @Override
+ public int addEntity(EntityBase e) {
if(e.isEntityInitialized())
throw new IllegalStateException("Entity already initialized");
@@ -132,4 +145,6 @@ public class World implements EntityStorage {
}
}
}
+
+
}