More porting prep, tune up invalidates and touches

This commit is contained in:
Mike Primm 2012-01-09 00:58:37 +08:00 committed by mikeprimm
parent 42418edf1f
commit 3db079f90f
10 changed files with 135 additions and 88 deletions

View File

@ -0,0 +1,16 @@
package org.dynmap;
/**
* Generic block location
*/
public class DynmapLocation {
public int x, y, z;
public String world;
public DynmapLocation() {}
public DynmapLocation(String w, int x, int y, int z) {
world = w;
this.x = x; this.y = y; this.z = z;
}
}

View File

@ -724,21 +724,31 @@ public class DynmapPlugin extends JavaPlugin implements DynmapAPI {
/* Register entity event triggers */ /* Register entity event triggers */
EntityListener entityTrigger = new EntityListener() { EntityListener entityTrigger = new EntityListener() {
private DynmapLocation dloc = new DynmapLocation();
private DynmapLocation toLoc(Location loc) {
dloc.x = loc.getBlockX(); dloc.y = loc.getBlockY();
dloc.z = loc.getBlockZ(); dloc.world = loc.getWorld().getName();
return dloc;
}
@Override @Override
public void onEntityExplode(EntityExplodeEvent event) { public void onEntityExplode(EntityExplodeEvent event) {
Location loc = event.getLocation();
String wname = loc.getWorld().getName();
int minx, maxx, miny, maxy, minz, maxz;
minx = maxx = loc.getBlockX();
miny = maxy = loc.getBlockY();
minz = maxz = loc.getBlockZ();
/* Calculate volume impacted by explosion */
List<Block> blocks = event.blockList(); List<Block> blocks = event.blockList();
for(Block b: blocks) { for(Block b: blocks) {
toLoc(b.getLocation()); Location l = b.getLocation();
mapManager.sscache.invalidateSnapshot(dloc); int x = l.getBlockX();
if(onexplosion) { if(x < minx) minx = x;
mapManager.touch(dloc, "entityexplode"); if(x > maxx) maxx = x;
} int y = l.getBlockY();
if(y < miny) miny = y;
if(y > maxy) maxy = y;
int z = l.getBlockZ();
if(z < minz) minz = z;
if(z > maxz) maxz = z;
}
mapManager.sscache.invalidateSnapshot(wname, minx, miny, minz, maxx, maxy, maxz);
if(onexplosion) {
mapManager.touchVolume(wname, minx, miny, minz, maxx, maxy, maxz, "entityexplode");
} }
} }
}; };
@ -755,21 +765,17 @@ public class DynmapPlugin extends JavaPlugin implements DynmapAPI {
return; return;
Chunk c = event.getChunk(); Chunk c = event.getChunk();
/* Touch extreme corners */ /* Touch extreme corners */
dloc.world = event.getWorld().getName(); int x = c.getX() << 4;
dloc.x = c.getX() << 4; int z = c.getZ() << 4;
dloc.y = 0; mapManager.touchVolume(event.getWorld().getName(), x, 0, z, x+15, 128, z+16, "chunkload");
dloc.z = c.getZ() << 4;
mapManager.touchVolume(dloc, 16, 128, 16, "chunkload");
} }
@Override @Override
public void onChunkPopulate(ChunkPopulateEvent event) { public void onChunkPopulate(ChunkPopulateEvent event) {
Chunk c = event.getChunk(); Chunk c = event.getChunk();
/* Touch extreme corners */ /* Touch extreme corners */
dloc.world = event.getWorld().getName(); int x = c.getX() << 4;
dloc.x = c.getX() << 4; int z = c.getZ() << 4;
dloc.y = 0; mapManager.touchVolume(event.getWorld().getName(), x, 0, z, x+15, 128, z+16, "chunkpopulate");
dloc.z = c.getZ() << 4;
mapManager.touchVolume(dloc, 16, 128, 16, "chunkpopulate");
} }
@Override @Override
public void onWorldLoad(WorldLoadEvent event) { public void onWorldLoad(WorldLoadEvent event) {
@ -1689,16 +1695,16 @@ public class DynmapPlugin extends JavaPlugin implements DynmapAPI {
public int triggerRenderOfVolume(Location l0, Location l1) { public int triggerRenderOfVolume(Location l0, Location l1) {
if(mapManager != null) { if(mapManager != null) {
if(l1 == null) if(l1 == null)
return mapManager.touch(toLoc(l0), "api"); return mapManager.touch(l0.getWorld().getName(), l0.getBlockX(), l0.getBlockY(), l0.getBlockZ(), "api");
else { else {
DynmapLocation dloc = toLoc(l0); int minx = Math.min(l0.getBlockX(), l1.getBlockX());
int sx = l1.getBlockX() - dloc.x + 1; int maxx = Math.max(l0.getBlockX(), l1.getBlockX());
int sy = l1.getBlockY() - dloc.y + 1; int miny = Math.min(l0.getBlockY(), l1.getBlockY());
int sz = l1.getBlockZ() - dloc.z + 1; int maxy = Math.max(l0.getBlockY(), l1.getBlockY());
if(sx < 1) { sx = -sx + 2; dloc.x = l1.getBlockX(); } int minz = Math.min(l0.getBlockZ(), l1.getBlockZ());
if(sy < 1) { sy = -sy + 2; dloc.y = l1.getBlockY(); } int maxz = Math.max(l0.getBlockZ(), l1.getBlockZ());
if(sz < 1) { sz = -sz + 2; dloc.z = l1.getBlockZ(); }
return mapManager.touchVolume(dloc, sx, sy, sz, "api"); return mapManager.touchVolume(l0.getWorld().getName(), minx, miny, minz, maxx, maxy, maxz, "api");
} }
} }
return 0; return 0;
@ -1867,12 +1873,20 @@ public class DynmapPlugin extends JavaPlugin implements DynmapAPI {
} }
@Override @Override
public int triggerRenderOfVolume(DynmapLocation loc, int sx, int sy, int sz) { public int triggerRenderOfBlock(String wid, int x, int y, int z) {
if(mapManager != null)
return mapManager.touch(wid, x, y, z, "api");
else
return 0;
}
@Override
public int triggerRenderOfVolume(String wid, int minx, int miny, int minz, int maxx, int maxy, int maxz) {
if(mapManager != null) { if(mapManager != null) {
if((sx == 1) && (sy == 1) && (sz == 1)) if((minx == maxx) && (miny == maxy) && (minz == maxz))
return mapManager.touch(loc, "api"); return mapManager.touch(wid, minx, miny, minz, "api");
else else
return mapManager.touchVolume(loc, sx, sy, sz, "api"); return mapManager.touchVolume(wid, minx, miny, minz, maxx, maxy, maxz, "api");
} }
return 0; return 0;
} }

View File

@ -453,7 +453,7 @@ public class MapManager {
renderedmaps.addAll(map.getMapsSharingRender(world)); renderedmaps.addAll(map.getMapsSharingRender(world));
/* Now, prime the render queue */ /* Now, prime the render queue */
for (MapTile mt : map.getTiles(loc)) { for (MapTile mt : map.getTiles(world, loc.x, loc.y, loc.z)) {
if (!found.getFlag(mt.tileOrdinalX(), mt.tileOrdinalY())) { if (!found.getFlag(mt.tileOrdinalX(), mt.tileOrdinalY())) {
found.setFlag(mt.tileOrdinalX(), mt.tileOrdinalY(), true); found.setFlag(mt.tileOrdinalX(), mt.tileOrdinalY(), true);
renderQueue.add(mt); renderQueue.add(mt);
@ -462,7 +462,7 @@ public class MapManager {
if(!updaterender) { /* Only add other seed points for fullrender */ if(!updaterender) { /* Only add other seed points for fullrender */
/* Add spawn location too (helps with some worlds where 0,64,0 may not be generated */ /* Add spawn location too (helps with some worlds where 0,64,0 may not be generated */
DynmapLocation sloc = world.getSpawnLocation(); DynmapLocation sloc = world.getSpawnLocation();
for (MapTile mt : map.getTiles(sloc)) { for (MapTile mt : map.getTiles(world, sloc.x, sloc.y, sloc.z)) {
if (!found.getFlag(mt.tileOrdinalX(), mt.tileOrdinalY())) { if (!found.getFlag(mt.tileOrdinalX(), mt.tileOrdinalY())) {
found.setFlag(mt.tileOrdinalX(), mt.tileOrdinalY(), true); found.setFlag(mt.tileOrdinalX(), mt.tileOrdinalY(), true);
renderQueue.add(mt); renderQueue.add(mt);
@ -470,7 +470,7 @@ public class MapManager {
} }
if(world.seedloc != null) { if(world.seedloc != null) {
for(DynmapLocation seed : world.seedloc) { for(DynmapLocation seed : world.seedloc) {
for (MapTile mt : map.getTiles(seed)) { for (MapTile mt : map.getTiles(world, seed.x, seed.y, seed.z)) {
if (!found.getFlag(mt.tileOrdinalX(),mt.tileOrdinalY())) { if (!found.getFlag(mt.tileOrdinalX(),mt.tileOrdinalY())) {
found.setFlag(mt.tileOrdinalX(),mt.tileOrdinalY(), true); found.setFlag(mt.tileOrdinalX(),mt.tileOrdinalY(), true);
renderQueue.add(mt); renderQueue.add(mt);
@ -1011,12 +1011,16 @@ public class MapManager {
} }
public int touch(DynmapLocation l, String reason) { public int touch(DynmapLocation l, String reason) {
DynmapWorld world = getWorld(l.world); return touch(l.world, l.x, l.y, l.z, reason);
}
public int touch(String wname, int x, int y, int z, String reason) {
DynmapWorld world = getWorld(wname);
if (world == null) if (world == null)
return 0; return 0;
int invalidates = 0; int invalidates = 0;
for (int i = 0; i < world.maps.size(); i++) { for (int i = 0; i < world.maps.size(); i++) {
MapTile[] tiles = world.maps.get(i).getTiles(l); MapTile[] tiles = world.maps.get(i).getTiles(world, x, y, z);
for (int j = 0; j < tiles.length; j++) { for (int j = 0; j < tiles.length; j++) {
if(invalidateTile(tiles[j])) if(invalidateTile(tiles[j]))
invalidates++; invalidates++;
@ -1037,13 +1041,13 @@ public class MapManager {
return invalidates; return invalidates;
} }
public int touchVolume(DynmapLocation l, int sx, int sy, int sz, String reason) { public int touchVolume(String wname, int minx, int miny, int minz, int maxx, int maxy, int maxz, String reason) {
DynmapWorld world = getWorld(l.world); DynmapWorld world = getWorld(wname);
if (world == null) if (world == null)
return 0; return 0;
int invalidates = 0; int invalidates = 0;
for (int i = 0; i < world.maps.size(); i++) { for (int i = 0; i < world.maps.size(); i++) {
MapTile[] tiles = world.maps.get(i).getTiles(l, sx, sy, sz); MapTile[] tiles = world.maps.get(i).getTiles(world, minx, miny, minz, maxx, maxy, maxz);
for (int j = 0; j < tiles.length; j++) { for (int j = 0; j < tiles.length; j++) {
if(invalidateTile(tiles[j])) if(invalidateTile(tiles[j]))
invalidates++; invalidates++;

View File

@ -37,9 +37,9 @@ public abstract class MapType {
public ZoomInfo(String pre, int bg) { prefix = pre; background_argb = bg; } public ZoomInfo(String pre, int bg) { prefix = pre; background_argb = bg; }
} }
public abstract MapTile[] getTiles(DynmapLocation l); public abstract MapTile[] getTiles(DynmapWorld w, int x, int y, int z);
public abstract MapTile[] getTiles(DynmapLocation l0, int sx, int sy, int sz); public abstract MapTile[] getTiles(DynmapWorld w, int minx, int miny, int minz, int maxx, int maxy, int maxz);
public abstract MapTile[] getAdjecentTiles(MapTile tile); public abstract MapTile[] getAdjecentTiles(MapTile tile);

View File

@ -85,21 +85,12 @@ public class FlatMap extends MapType {
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation l) { public MapTile[] getTiles(DynmapWorld w, int x, int y, int z) {
DynmapWorld w = MapManager.mapman.getWorld(l.world); return new MapTile[] { new FlatMapTile(w, this, x>>7, z>>7, 128) };
return new MapTile[] { new FlatMapTile(w, this, (int) Math.floor(l.x / 128.0), (int) Math.floor(l.z / 128.0), 128) };
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation l, int sx, int sy, int sz) { public MapTile[] getTiles(DynmapWorld w, int xmin, int ymin, int zmin, int xmax, int ymax, int zmax) {
DynmapWorld w = MapManager.mapman.getWorld(l.world);
int xmin, xmax, zmin, zmax;
xmin = l.x >> 7;
zmin = l.z >> 7;
xmax = (l.x + sx) >> 7;
zmax = (l.z + sz) >> 7;
ArrayList<MapTile> rslt = new ArrayList<MapTile>(); ArrayList<MapTile> rslt = new ArrayList<MapTile>();
for(int i = xmin; i <= xmax; i++) { for(int i = xmin; i <= xmax; i++) {
for(int j = zmin; j < zmax; j++) { for(int j = zmin; j < zmax; j++) {

View File

@ -128,13 +128,13 @@ public class HDMap extends MapType {
public HDLighting getLighting() { return lighting; } public HDLighting getLighting() { return lighting; }
@Override @Override
public MapTile[] getTiles(DynmapLocation loc) { public MapTile[] getTiles(DynmapWorld w, int x, int y, int z) {
return perspective.getTiles(loc); return perspective.getTiles(w, x, y, z);
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation loc, int sx, int sy, int sz) { public MapTile[] getTiles(DynmapWorld w, int minx, int miny, int minz, int maxx, int maxy, int maxz) {
return perspective.getTiles(loc, sx, sy, sz); return perspective.getTiles(w, minx, miny, minz, maxx, maxy, maxz);
} }
@Override @Override

View File

@ -4,6 +4,7 @@ import java.util.List;
import org.dynmap.DynmapChunk; import org.dynmap.DynmapChunk;
import org.dynmap.DynmapLocation; import org.dynmap.DynmapLocation;
import org.dynmap.DynmapWorld;
import org.dynmap.MapTile; import org.dynmap.MapTile;
import org.dynmap.utils.MapChunkCache; import org.dynmap.utils.MapChunkCache;
import org.json.simple.JSONObject; import org.json.simple.JSONObject;
@ -12,9 +13,9 @@ public interface HDPerspective {
/* Get name of perspective */ /* Get name of perspective */
String getName(); String getName();
/* Get tiles invalidated by change at given location */ /* Get tiles invalidated by change at given location */
MapTile[] getTiles(DynmapLocation loc); MapTile[] getTiles(DynmapWorld w, int x, int y, int z);
/* Get tiles invalidated by change at given volume, defined by 2 opposite corner locations */ /* Get tiles invalidated by change at given volume, defined by 2 opposite corner locations */
MapTile[] getTiles(DynmapLocation loc0, int sx, int sy, int sz); MapTile[] getTiles(DynmapWorld w, int minx, int miny, int minz, int maxx, int maxy, int maxz);
/* Get tiles adjacent to given tile */ /* Get tiles adjacent to given tile */
MapTile[] getAdjecentTiles(MapTile tile); MapTile[] getAdjecentTiles(MapTile tile);
/* Get chunks needed for given tile */ /* Get chunks needed for given tile */

View File

@ -816,11 +816,12 @@ public class IsoHDPerspective implements HDPerspective {
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation loc) { public MapTile[] getTiles(DynmapWorld world, int x, int y, int z) {
DynmapWorld world = MapManager.mapman.getWorld(loc.world);
HashSet<MapTile> tiles = new HashSet<MapTile>(); HashSet<MapTile> tiles = new HashSet<MapTile>();
Vector3D block = new Vector3D(); Vector3D block = new Vector3D();
block.setFromLocation(loc); /* Get coordinate for block */ block.x = x;
block.y = y;
block.z = z;
Vector3D corner = new Vector3D(); Vector3D corner = new Vector3D();
/* Loop through corners of the cube */ /* Loop through corners of the cube */
for(int i = 0; i < 2; i++) { for(int i = 0; i < 2; i++) {
@ -843,16 +844,15 @@ public class IsoHDPerspective implements HDPerspective {
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation loc, int sx, int sy, int sz) { public MapTile[] getTiles(DynmapWorld world, int minx, int miny, int minz, int maxx, int maxy, int maxz) {
DynmapWorld world = MapManager.mapman.getWorld(loc.world);
HashSet<MapTile> tiles = new HashSet<MapTile>(); HashSet<MapTile> tiles = new HashSet<MapTile>();
Vector3D blocks[] = new Vector3D[] { new Vector3D(), new Vector3D() }; Vector3D blocks[] = new Vector3D[] { new Vector3D(), new Vector3D() };
blocks[0].x = loc.x - 1; blocks[0].x = minx - 1;
blocks[0].y = loc.y - 1; blocks[0].y = miny - 1;
blocks[0].z = loc.z - 1; blocks[0].z = minz - 1;
blocks[1].x = loc.x + sx; blocks[1].x = maxx + 1;
blocks[1].y = loc.y + sy; blocks[1].y = maxy + 1;
blocks[1].z = loc.z + sz; blocks[1].z = maxz + 1;
Vector3D corner = new Vector3D(); Vector3D corner = new Vector3D();
Vector3D tcorner = new Vector3D(); Vector3D tcorner = new Vector3D();

View File

@ -50,13 +50,7 @@ public class KzedMap extends MapType {
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation l) { public MapTile[] getTiles(DynmapWorld world, int x, int y, int z) {
DynmapWorld world = MapManager.mapman.getWorld(l.world);
int x = l.x;
int y = l.y;
int z = l.z;
int dx = x - anchorx; int dx = x - anchorx;
int dy = y - anchory; int dy = y - anchory;
int dz = z - anchorz; int dz = z - anchorz;
@ -99,18 +93,17 @@ public class KzedMap extends MapType {
} }
@Override @Override
public MapTile[] getTiles(DynmapLocation loc, int sx, int sy, int sz) { public MapTile[] getTiles(DynmapWorld world, int minx, int miny, int minz, int maxx, int maxy, int maxz) {
DynmapWorld world = MapManager.mapman.getWorld(loc.world);
ArrayList<MapTile> tiles = new ArrayList<MapTile>(); ArrayList<MapTile> tiles = new ArrayList<MapTile>();
/* Transform both to tile coordinates */ /* Transform both to tile coordinates */
int dx = loc.x - anchorx; int dx = minx - anchorx;
int dy = loc.y - anchory; int dy = miny - anchory;
int dz = loc.z - anchorz; int dz = minz - anchorz;
int px0 = dx + dz; int px0 = dx + dz;
int py0 = dx - dz - dy; int py0 = dx - dz - dy;
dx = loc.x + sx - anchorx; dx = maxx - anchorx;
dy = loc.y + sy - anchory; dy = maxy - anchory;
dz = loc.z + sz - anchorz; dz = maxz - anchorz;
int px1 = dx + dz; int px1 = dx + dz;
int py1 = dx - dz - dy; int py1 = dx - dz - dy;
/* Compute ranges */ /* Compute ranges */

View File

@ -67,6 +67,34 @@ public class SnapshotCache {
} }
processRefQueue(); processRefQueue();
} }
/**
* Invalidate cached snapshot, if in cache
*/
public void invalidateSnapshot(String w, int x, int y, int z) {
String key = getKey(w, x>>4, z>>4);
CacheRec rec = snapcache.remove(key);
if(rec != null) {
snapcache.reverselookup.remove(rec.ref);
rec.ref.clear();
}
processRefQueue();
}
/**
* Invalidate cached snapshot, if in cache
*/
public void invalidateSnapshot(String w, int x0, int y0, int z0, int x1, int y1, int z1) {
for(int xx = (x0>>4); xx <= (x1>>4); xx++) {
for(int zz = (z0>>4); zz <= (z1>>4); zz++) {
String key = getKey(w, xx, zz);
CacheRec rec = snapcache.remove(key);
if(rec != null) {
snapcache.reverselookup.remove(rec.ref);
rec.ref.clear();
}
}
}
processRefQueue();
}
/** /**
* Look for chunk snapshot in cache * Look for chunk snapshot in cache
*/ */