mirror of
https://github.com/webbukkit/dynmap.git
synced 2024-11-24 03:05:28 +01:00
Add performance tweaks on DynmapBlockState
This commit is contained in:
parent
fae704b899
commit
99d5416acb
@ -554,6 +554,8 @@ public class DynmapCore implements DynmapCommonAPI {
|
|||||||
|
|
||||||
/* Process mod support */
|
/* Process mod support */
|
||||||
ModSupportImpl.complete(this.dataDirectory);
|
ModSupportImpl.complete(this.dataDirectory);
|
||||||
|
// Finalize block state
|
||||||
|
DynmapBlockState.finalizeBlockStates();
|
||||||
/* Load block models */
|
/* Load block models */
|
||||||
Log.verboseinfo("Loading models...");
|
Log.verboseinfo("Loading models...");
|
||||||
HDBlockModels.loadModels(this, configuration);
|
HDBlockModels.loadModels(this, configuration);
|
||||||
|
@ -3,6 +3,8 @@ package org.dynmap.renderer;
|
|||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.HashSet;
|
import java.util.HashSet;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
|
||||||
// This represents a distinct block state value for a simple block from the world data.
|
// This represents a distinct block state value for a simple block from the world data.
|
||||||
// Each distinct persistent block state from the world data will map to exactly one instance of this class, such that
|
// Each distinct persistent block state from the world data will map to exactly one instance of this class, such that
|
||||||
@ -48,6 +50,9 @@ public class DynmapBlockState {
|
|||||||
private static HashMap<Integer, DynmapBlockState> blocksByIndex = new HashMap<Integer, DynmapBlockState>();
|
private static HashMap<Integer, DynmapBlockState> blocksByIndex = new HashMap<Integer, DynmapBlockState>();
|
||||||
// Map of base states by legacy ID
|
// Map of base states by legacy ID
|
||||||
private static HashMap<Integer, DynmapBlockState> blocksByLegacyID = new HashMap<Integer, DynmapBlockState>();
|
private static HashMap<Integer, DynmapBlockState> blocksByLegacyID = new HashMap<Integer, DynmapBlockState>();
|
||||||
|
// Array lookup by global state index (faster than map)
|
||||||
|
private static DynmapBlockState[] blockArrayByIndex = null;
|
||||||
|
private static DynmapBlockState[] blockArrayByLegacyID = null;
|
||||||
|
|
||||||
// Well known block names (some versions might need to overwrite these)
|
// Well known block names (some versions might need to overwrite these)
|
||||||
public static String AIR_BLOCK = "minecraft:air";
|
public static String AIR_BLOCK = "minecraft:air";
|
||||||
@ -107,6 +112,13 @@ public class DynmapBlockState {
|
|||||||
* @param legacyblkid - legacy block ID (if defined), otherwise -1
|
* @param legacyblkid - legacy block ID (if defined), otherwise -1
|
||||||
*/
|
*/
|
||||||
public DynmapBlockState(DynmapBlockState base, int stateidx, String blkname, String statename, String material, int legacyblkid) {
|
public DynmapBlockState(DynmapBlockState base, int stateidx, String blkname, String statename, String material, int legacyblkid) {
|
||||||
|
// If we generated lookup arrays, flush them and complain about it
|
||||||
|
if (blockArrayByIndex != null) {
|
||||||
|
blockArrayByIndex = null;
|
||||||
|
blockArrayByLegacyID = null;
|
||||||
|
System.err.println("Error: DynmapBlockState updated after arrays generated");
|
||||||
|
Thread.dumpStack();
|
||||||
|
}
|
||||||
globalStateIndex = (nextGlobalStateIndex++); // Assign index
|
globalStateIndex = (nextGlobalStateIndex++); // Assign index
|
||||||
if (base == null) base = this;
|
if (base == null) base = this;
|
||||||
baseState = base;
|
baseState = base;
|
||||||
@ -118,17 +130,21 @@ public class DynmapBlockState {
|
|||||||
}
|
}
|
||||||
blockName = blkname;
|
blockName = blkname;
|
||||||
stateName = (statename != null) ? statename : "";
|
stateName = (statename != null) ? statename : "";
|
||||||
|
|
||||||
|
if (stateIndex > 4096) {
|
||||||
|
System.out.println(String.format("DynmapBlockStste(%d, %s, %s, %s, %d)", stateidx, blkname, statename, material, legacyblkid));
|
||||||
|
Thread.dumpStack();
|
||||||
|
}
|
||||||
if (base != this) { // If we aren't base block state
|
if (base != this) { // If we aren't base block state
|
||||||
if (base.states == null) { // If no state list yet
|
if (base.states == null) { // If no state list yet
|
||||||
base.states = new DynmapBlockState[Math.max(stateidx+1, 16)]; // Enough for us to fit (at least 16
|
base.states = new DynmapBlockState[stateidx+1]; // Enough for us to fit
|
||||||
Arrays.fill(base.states, AIR);
|
Arrays.fill(base.states, AIR);
|
||||||
base.states[0] = base; // Add base state as index 0
|
base.states[0] = base; // Add base state as index 0
|
||||||
}
|
}
|
||||||
else if (base.states.length <= stateidx) { // Not enough room
|
else if (base.states.length <= stateidx) { // Not enough room
|
||||||
// Resize it
|
// Resize it
|
||||||
DynmapBlockState[] newstates = new DynmapBlockState[Math.max((stateidx * 3) / 2, 32)]; // Get some extra (logN scaling for big state spaces)
|
DynmapBlockState[] newstates = Arrays.copyOf(base.states, stateidx+1);
|
||||||
System.arraycopy(base.states, 0, newstates, 0, base.states.length);
|
Arrays.fill(newstates, base.states.length, newstates.length, AIR);
|
||||||
Arrays.fill(newstates, base.states.length, stateidx+1, AIR);
|
|
||||||
base.states = newstates;
|
base.states = newstates;
|
||||||
}
|
}
|
||||||
base.states[stateidx] = this;
|
base.states[stateidx] = this;
|
||||||
@ -160,6 +176,26 @@ public class DynmapBlockState {
|
|||||||
still_water = this;
|
still_water = this;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Generate static lookup arrays once all BlockStates initialized
|
||||||
|
*/
|
||||||
|
public static void finalizeBlockStates() {
|
||||||
|
// Build blockArrayByIndex
|
||||||
|
blockArrayByIndex = new DynmapBlockState[nextGlobalStateIndex];
|
||||||
|
Arrays.fill(blockArrayByIndex, AIR);
|
||||||
|
for (Map.Entry<Integer, DynmapBlockState> rec : blocksByIndex.entrySet()) {
|
||||||
|
blockArrayByIndex[rec.getKey().intValue()] = rec.getValue();
|
||||||
|
}
|
||||||
|
// Build blockArrayByLegacyID
|
||||||
|
int maxLegacyID = 0;
|
||||||
|
for (Map.Entry<Integer, DynmapBlockState> rec : blocksByLegacyID.entrySet()) {
|
||||||
|
maxLegacyID = Math.max(maxLegacyID, rec.getKey());
|
||||||
|
}
|
||||||
|
blockArrayByLegacyID = new DynmapBlockState[maxLegacyID+1];
|
||||||
|
for (Map.Entry<Integer, DynmapBlockState> rec : blocksByLegacyID.entrySet()) {
|
||||||
|
blockArrayByLegacyID[rec.getKey().intValue()] = rec.getValue();
|
||||||
|
}
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
* Get state for same base block with given index
|
* Get state for same base block with given index
|
||||||
* @param idx - index number
|
* @param idx - index number
|
||||||
@ -211,6 +247,13 @@ public class DynmapBlockState {
|
|||||||
* @return block state, or AIR if not found
|
* @return block state, or AIR if not found
|
||||||
*/
|
*/
|
||||||
public static final DynmapBlockState getStateByGlobalIndex(int gidx) {
|
public static final DynmapBlockState getStateByGlobalIndex(int gidx) {
|
||||||
|
if (blockArrayByIndex != null) {
|
||||||
|
try {
|
||||||
|
return blockArrayByIndex[gidx];
|
||||||
|
} catch (ArrayIndexOutOfBoundsException aioob) {
|
||||||
|
return AIR;
|
||||||
|
}
|
||||||
|
}
|
||||||
DynmapBlockState bs = blocksByIndex.get(gidx);
|
DynmapBlockState bs = blocksByIndex.get(gidx);
|
||||||
return (bs != null) ? bs : AIR;
|
return (bs != null) ? bs : AIR;
|
||||||
}
|
}
|
||||||
@ -220,6 +263,13 @@ public class DynmapBlockState {
|
|||||||
* @return block base state, or null if not found
|
* @return block base state, or null if not found
|
||||||
*/
|
*/
|
||||||
public static final DynmapBlockState getStateByLegacyBlockID(int legacyid) {
|
public static final DynmapBlockState getStateByLegacyBlockID(int legacyid) {
|
||||||
|
if (blockArrayByLegacyID != null) {
|
||||||
|
try {
|
||||||
|
return blockArrayByLegacyID[legacyid];
|
||||||
|
} catch (ArrayIndexOutOfBoundsException aioob) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
return blocksByLegacyID.get(legacyid);
|
return blocksByLegacyID.get(legacyid);
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
|
Loading…
Reference in New Issue
Block a user