Some more performance tweaks
This commit is contained in:
parent
a2c81c9a91
commit
0664472a6b
4 changed files with 118 additions and 217 deletions
|
|
@ -19,7 +19,8 @@ public abstract class HDBlockModel {
|
||||||
for (int i = 0; i < bblk.getStateCount(); i++) {
|
for (int i = 0; i < bblk.getStateCount(); i++) {
|
||||||
if (databits.isEmpty() || databits.get(i)) {
|
if (databits.isEmpty() || databits.get(i)) {
|
||||||
DynmapBlockState bs = bblk.getState(i);
|
DynmapBlockState bs = bblk.getState(i);
|
||||||
HDBlockModel prev = HDBlockModels.models_by_id_data.put(bs.globalStateIndex, this);
|
HDBlockModel prev = HDBlockModels.models_by_id_data[bs.globalStateIndex];
|
||||||
|
HDBlockModels.models_by_id_data[bs.globalStateIndex] = this;
|
||||||
if((prev != null) && (prev != this)) {
|
if((prev != null) && (prev != this)) {
|
||||||
prev.removed(bs);
|
prev.removed(bs);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -41,7 +41,7 @@ import org.dynmap.utils.Vector3D;
|
||||||
*/
|
*/
|
||||||
public class HDBlockModels {
|
public class HDBlockModels {
|
||||||
private static int max_patches;
|
private static int max_patches;
|
||||||
static HashMap<Integer, HDBlockModel> models_by_id_data = new HashMap<Integer, HDBlockModel>();
|
static HDBlockModel[] models_by_id_data = new HDBlockModel[0];
|
||||||
static PatchDefinitionFactory pdf = new PatchDefinitionFactory();
|
static PatchDefinitionFactory pdf = new PatchDefinitionFactory();
|
||||||
static BitSet customModelsRequestingTileData = new BitSet(); // Index by globalStateIndex
|
static BitSet customModelsRequestingTileData = new BitSet(); // Index by globalStateIndex
|
||||||
static BitSet changeIgnoredBlocks = new BitSet(); // Index by globalStateIndex
|
static BitSet changeIgnoredBlocks = new BitSet(); // Index by globalStateIndex
|
||||||
|
|
@ -53,17 +53,19 @@ public class HDBlockModels {
|
||||||
|
|
||||||
/* Reset model if defined by different block set */
|
/* Reset model if defined by different block set */
|
||||||
public static boolean resetIfNotBlockSet(DynmapBlockState blk, String blockset) {
|
public static boolean resetIfNotBlockSet(DynmapBlockState blk, String blockset) {
|
||||||
HDBlockModel bm = models_by_id_data.get(blk.globalStateIndex);
|
int idx = blk.globalStateIndex;
|
||||||
|
HDBlockModel bm = (idx < models_by_id_data.length) ? models_by_id_data[idx] : null;
|
||||||
if((bm != null) && (bm.getBlockSet().equals(blockset) == false)) {
|
if((bm != null) && (bm.getBlockSet().equals(blockset) == false)) {
|
||||||
Debug.debug("Reset block model for " + blk + " from " + bm.getBlockSet() + " due to new def from " + blockset);
|
Debug.debug("Reset block model for " + blk + " from " + bm.getBlockSet() + " due to new def from " + blockset);
|
||||||
models_by_id_data.remove(blk.globalStateIndex);
|
models_by_id_data[idx] = null;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
/* Get texture count needed for model */
|
/* Get texture count needed for model */
|
||||||
public static int getNeededTextureCount(DynmapBlockState blk) {
|
public static int getNeededTextureCount(DynmapBlockState blk) {
|
||||||
HDBlockModel bm = models_by_id_data.get(blk.globalStateIndex);
|
int idx = blk.globalStateIndex;
|
||||||
|
HDBlockModel bm = (idx < models_by_id_data.length) ? models_by_id_data[idx] : null;
|
||||||
if(bm != null) {
|
if(bm != null) {
|
||||||
return bm.getTextureCount();
|
return bm.getTextureCount();
|
||||||
}
|
}
|
||||||
|
|
@ -88,18 +90,12 @@ public class HDBlockModels {
|
||||||
|
|
||||||
private static void remapModel(String bn, String newbn) {
|
private static void remapModel(String bn, String newbn) {
|
||||||
DynmapBlockState frombs = DynmapBlockState.getBaseStateByName(bn);
|
DynmapBlockState frombs = DynmapBlockState.getBaseStateByName(bn);
|
||||||
DynmapBlockState tobs = DynmapBlockState.getBaseStateByName(bn);
|
DynmapBlockState tobs = DynmapBlockState.getBaseStateByName(newbn);
|
||||||
int fcnt = frombs.getStateCount();
|
int fcnt = frombs.getStateCount();
|
||||||
for (int bs = 0; bs < tobs.getStateCount(); bs++) {
|
for (int bs = 0; bs < tobs.getStateCount(); bs++) {
|
||||||
DynmapBlockState tb = tobs.getState(bs);
|
DynmapBlockState tb = tobs.getState(bs);
|
||||||
DynmapBlockState fs = tobs.getState(bs % fcnt);
|
DynmapBlockState fs = frombs.getState(bs % fcnt);
|
||||||
HDBlockModel m = models_by_id_data.get(fs.globalStateIndex);
|
models_by_id_data[tb.globalStateIndex] = models_by_id_data[fs.globalStateIndex];
|
||||||
if (m != null) {
|
|
||||||
models_by_id_data.put(tb.globalStateIndex, m);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
models_by_id_data.remove(tb.globalStateIndex);
|
|
||||||
}
|
|
||||||
customModelsRequestingTileData.set(tb.globalStateIndex, customModelsRequestingTileData.get(fs.globalStateIndex));
|
customModelsRequestingTileData.set(tb.globalStateIndex, customModelsRequestingTileData.get(fs.globalStateIndex));
|
||||||
changeIgnoredBlocks.set(tb.globalStateIndex, changeIgnoredBlocks.get(fs.globalStateIndex));
|
changeIgnoredBlocks.set(tb.globalStateIndex, changeIgnoredBlocks.get(fs.globalStateIndex));
|
||||||
}
|
}
|
||||||
|
|
@ -113,7 +109,7 @@ public class HDBlockModels {
|
||||||
public static final String[] getTileEntityFieldsNeeded(DynmapBlockState blk) {
|
public static final String[] getTileEntityFieldsNeeded(DynmapBlockState blk) {
|
||||||
int idx = blk.globalStateIndex;
|
int idx = blk.globalStateIndex;
|
||||||
if(customModelsRequestingTileData.get(idx)) {
|
if(customModelsRequestingTileData.get(idx)) {
|
||||||
HDBlockModel mod = models_by_id_data.get(idx);
|
HDBlockModel mod = (idx < models_by_id_data.length) ? models_by_id_data[idx] : null;
|
||||||
if(mod instanceof CustomBlockModel) {
|
if(mod instanceof CustomBlockModel) {
|
||||||
return ((CustomBlockModel)mod).render.getTileEntityFieldsNeeded();
|
return ((CustomBlockModel)mod).render.getTileEntityFieldsNeeded();
|
||||||
}
|
}
|
||||||
|
|
@ -166,7 +162,7 @@ public class HDBlockModels {
|
||||||
File datadir = core.getDataFolder();
|
File datadir = core.getDataFolder();
|
||||||
max_patches = 6; /* Reset to default */
|
max_patches = 6; /* Reset to default */
|
||||||
/* Reset models-by-ID-Data cache */
|
/* Reset models-by-ID-Data cache */
|
||||||
models_by_id_data.clear();
|
models_by_id_data = new HDBlockModel[DynmapBlockState.getGlobalIndexMax()];
|
||||||
/* Reset scaled models by scale cache */
|
/* Reset scaled models by scale cache */
|
||||||
scaled_models_by_scale.clear();
|
scaled_models_by_scale.clear();
|
||||||
/* Reset change-ignored flags */
|
/* Reset change-ignored flags */
|
||||||
|
|
@ -455,7 +451,7 @@ public class HDBlockModels {
|
||||||
Log.severe("Invalid rotate ID: " + bs + " on line " + lineNum + " of file: " + fname);
|
Log.severe("Invalid rotate ID: " + bs + " on line " + lineNum + " of file: " + fname);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
HDBlockModel mod = models_by_id_data.get(bs.globalStateIndex);
|
HDBlockModel mod = models_by_id_data[bs.globalStateIndex];
|
||||||
if (modlist.isEmpty()) {
|
if (modlist.isEmpty()) {
|
||||||
}
|
}
|
||||||
else if ((mod != null) && ((rot%90) == 0) && (mod instanceof HDBlockVolumetricModel)) {
|
else if ((mod != null) && ((rot%90) == 0) && (mod instanceof HDBlockVolumetricModel)) {
|
||||||
|
|
@ -524,7 +520,7 @@ public class HDBlockModels {
|
||||||
Log.severe("Invalid patchrotate ID: " + bs + " on line " + lineNum + "of file: " + fname);
|
Log.severe("Invalid patchrotate ID: " + bs + " on line " + lineNum + "of file: " + fname);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
HDBlockModel mod = models_by_id_data.get(bs.globalStateIndex);
|
HDBlockModel mod = models_by_id_data[bs.globalStateIndex];
|
||||||
if (pmodlist.isEmpty()) {
|
if (pmodlist.isEmpty()) {
|
||||||
}
|
}
|
||||||
else if ((mod != null) && (mod instanceof HDBlockPatchModel)) {
|
else if ((mod != null) && (mod instanceof HDBlockPatchModel)) {
|
||||||
|
|
|
||||||
|
|
@ -21,9 +21,10 @@ public class HDScaledBlockModels {
|
||||||
newcustom = new CustomBlockModel[DynmapBlockState.getGlobalIndexMax()];
|
newcustom = new CustomBlockModel[DynmapBlockState.getGlobalIndexMax()];
|
||||||
custom = newcustom;
|
custom = newcustom;
|
||||||
}
|
}
|
||||||
for(Integer gidx : HDBlockModels.models_by_id_data.keySet()) {
|
for(int gidx = 0; gidx < HDBlockModels.models_by_id_data.length; gidx++) {
|
||||||
HDBlockModel m = HDBlockModels.models_by_id_data.get(gidx);
|
HDBlockModel m = HDBlockModels.models_by_id_data[gidx];
|
||||||
|
if(m == null) continue;
|
||||||
|
|
||||||
if(m instanceof HDBlockVolumetricModel) {
|
if(m instanceof HDBlockVolumetricModel) {
|
||||||
HDBlockVolumetricModel vm = (HDBlockVolumetricModel)m;
|
HDBlockVolumetricModel vm = (HDBlockVolumetricModel)m;
|
||||||
short[] smod = vm.getScaledMap(scale);
|
short[] smod = vm.getScaledMap(scale);
|
||||||
|
|
@ -58,37 +59,34 @@ public class HDScaledBlockModels {
|
||||||
}
|
}
|
||||||
|
|
||||||
public final short[] getScaledModel(DynmapBlockState blk) {
|
public final short[] getScaledModel(DynmapBlockState blk) {
|
||||||
short[] m = null;
|
int idx = blk.globalStateIndex;
|
||||||
try {
|
if(idx >= modelvectors.length) {
|
||||||
m = modelvectors[blk.globalStateIndex];
|
short[][] newmodels = new short[idx + 1][];
|
||||||
} catch (ArrayIndexOutOfBoundsException aioobx) {
|
|
||||||
short[][] newmodels = new short[blk.globalStateIndex+1][];
|
|
||||||
System.arraycopy(modelvectors, 0, newmodels, 0, modelvectors.length);
|
System.arraycopy(modelvectors, 0, newmodels, 0, modelvectors.length);
|
||||||
modelvectors = newmodels;
|
modelvectors = newmodels;
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
return m;
|
return modelvectors[idx];
|
||||||
}
|
}
|
||||||
public PatchDefinition[] getPatchModel(DynmapBlockState blk) {
|
public PatchDefinition[] getPatchModel(DynmapBlockState blk) {
|
||||||
PatchDefinition[] p = null;
|
int idx = blk.globalStateIndex;
|
||||||
try {
|
if(idx >= patches.length) {
|
||||||
p = patches[blk.globalStateIndex];
|
PatchDefinition[][] newpatches = new PatchDefinition[idx + 1][];
|
||||||
} catch (ArrayIndexOutOfBoundsException aioobx) {
|
|
||||||
PatchDefinition[][] newpatches = new PatchDefinition[blk.globalStateIndex+1][];
|
|
||||||
System.arraycopy(patches, 0, newpatches, 0, patches.length);
|
System.arraycopy(patches, 0, newpatches, 0, patches.length);
|
||||||
patches = newpatches;
|
patches = newpatches;
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
return p;
|
return patches[idx];
|
||||||
}
|
}
|
||||||
|
|
||||||
public CustomBlockModel getCustomBlockModel(DynmapBlockState blk) {
|
public CustomBlockModel getCustomBlockModel(DynmapBlockState blk) {
|
||||||
CustomBlockModel m = null;
|
int idx = blk.globalStateIndex;
|
||||||
try {
|
if(idx >= custom.length) {
|
||||||
m = custom[blk.globalStateIndex];
|
CustomBlockModel[] newcustom = new CustomBlockModel[idx + 1];
|
||||||
} catch (ArrayIndexOutOfBoundsException aioobx) {
|
|
||||||
CustomBlockModel[] newcustom = new CustomBlockModel[blk.globalStateIndex+1];
|
|
||||||
System.arraycopy(custom, 0, newcustom, 0, custom.length);
|
System.arraycopy(custom, 0, newcustom, 0, custom.length);
|
||||||
custom = newcustom;
|
custom = newcustom;
|
||||||
}
|
return null;
|
||||||
return m;
|
}
|
||||||
|
return custom[idx];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -45,208 +45,119 @@ public class ShadowHDLighting extends DefaultHDLighting {
|
||||||
smooth = configuration.getBoolean("smooth-lighting", MapManager.mapman.getSmoothLighting());
|
smooth = configuration.getBoolean("smooth-lighting", MapManager.mapman.getSmoothLighting());
|
||||||
}
|
}
|
||||||
|
|
||||||
private void applySmoothLighting(HDPerspectiveState ps, HDShaderState ss, Color incolor, Color[] outcolor, int[] shadowscale) {
|
private void applySmoothLighting(HDPerspectiveState ps, HDShaderState ss, Color incolor, Color[] outcolor, int[] shadowscale) {
|
||||||
int[] xyz = ps.getSubblockCoord();
|
int[] xyz = ps.getSubblockCoord();
|
||||||
int scale = (int)ps.getScale();
|
int scale = (int)ps.getScale();
|
||||||
int mid = scale/2;
|
int mid = scale / 2;
|
||||||
BlockStep s1, s2;
|
BlockStep s1, s2;
|
||||||
int w1, w2;
|
int w1, w2;
|
||||||
/* Figure out which directions to look */
|
/* Figure out which two neighbor directions to sample */
|
||||||
switch(ps.getLastBlockStep()) {
|
switch(ps.getLastBlockStep()) {
|
||||||
case X_MINUS:
|
case X_MINUS:
|
||||||
case X_PLUS:
|
case X_PLUS:
|
||||||
if(xyz[1] < mid) {
|
s1 = (xyz[1] < mid) ? BlockStep.Y_MINUS : BlockStep.Y_PLUS;
|
||||||
s1 = BlockStep.Y_MINUS;
|
w1 = Math.abs(xyz[1] - mid);
|
||||||
w1 = mid - xyz[1];
|
s2 = (xyz[2] < mid) ? BlockStep.Z_MINUS : BlockStep.Z_PLUS;
|
||||||
}
|
w2 = Math.abs(xyz[2] - mid);
|
||||||
else {
|
|
||||||
s1 = BlockStep.Y_PLUS;
|
|
||||||
w1 = xyz[1] - mid;
|
|
||||||
}
|
|
||||||
if(xyz[2] < mid) {
|
|
||||||
s2 = BlockStep.Z_MINUS;
|
|
||||||
w2 = mid - xyz[2];
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
s2 = BlockStep.Z_PLUS;
|
|
||||||
w2 = xyz[2] - mid;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case Z_MINUS:
|
case Z_MINUS:
|
||||||
case Z_PLUS:
|
case Z_PLUS:
|
||||||
if(xyz[0] < mid) {
|
s1 = (xyz[0] < mid) ? BlockStep.X_MINUS : BlockStep.X_PLUS;
|
||||||
s1 = BlockStep.X_MINUS;
|
w1 = Math.abs(xyz[0] - mid);
|
||||||
w1 = mid - xyz[0];
|
s2 = (xyz[1] < mid) ? BlockStep.Y_MINUS : BlockStep.Y_PLUS;
|
||||||
}
|
w2 = Math.abs(xyz[1] - mid);
|
||||||
else {
|
|
||||||
s1 = BlockStep.X_PLUS;
|
|
||||||
w1 = xyz[0] - mid;
|
|
||||||
}
|
|
||||||
if(xyz[1] < mid) {
|
|
||||||
s2 = BlockStep.Y_MINUS;
|
|
||||||
w2 = mid - xyz[1];
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
s2 = BlockStep.Y_PLUS;
|
|
||||||
w2 = xyz[1] - mid;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
if(xyz[0] < mid) {
|
s1 = (xyz[0] < mid) ? BlockStep.X_MINUS : BlockStep.X_PLUS;
|
||||||
s1 = BlockStep.X_MINUS;
|
w1 = Math.abs(xyz[0] - mid);
|
||||||
w1 = mid - xyz[0];
|
s2 = (xyz[2] < mid) ? BlockStep.Z_MINUS : BlockStep.Z_PLUS;
|
||||||
}
|
w2 = Math.abs(xyz[2] - mid);
|
||||||
else {
|
|
||||||
s1 = BlockStep.X_PLUS;
|
|
||||||
w1 = xyz[0] - mid;
|
|
||||||
}
|
|
||||||
if(xyz[2] < mid) {
|
|
||||||
s2 = BlockStep.Z_MINUS;
|
|
||||||
w2 = mid - xyz[2];
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
s2 = BlockStep.Z_PLUS;
|
|
||||||
w2 = xyz[2] - mid;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
/* Now get the 3 needed light levels */
|
/* Fetch the 3 needed light levels (once, shared by both night and day passes) */
|
||||||
LightLevels skyemit0 = ps.getCachedLightLevels(0);
|
LightLevels ll0 = ps.getCachedLightLevels(0);
|
||||||
ps.getLightLevels(skyemit0);
|
ps.getLightLevels(ll0);
|
||||||
LightLevels skyemit1 = ps.getCachedLightLevels(1);
|
LightLevels ll1 = ps.getCachedLightLevels(1);
|
||||||
ps.getLightLevelsAtStep(s1, skyemit1);
|
ps.getLightLevelsAtStep(s1, ll1);
|
||||||
LightLevels skyemit2 = ps.getCachedLightLevels(2);
|
LightLevels ll2 = ps.getCachedLightLevels(2);
|
||||||
ps.getLightLevelsAtStep(s2, skyemit2);
|
ps.getLightLevelsAtStep(s2, ll2);
|
||||||
|
|
||||||
/* Get light levels */
|
/* Night (ambient) pass */
|
||||||
int ll0 = getLightLevel(skyemit0, true);
|
applySmoothedLightToColor(outcolor[0], incolor, ll0, ll1, ll2, true, w1, w2, scale, shadowscale);
|
||||||
int ll1 = getLightLevel(skyemit1, true);
|
/* Day pass (only when night/day rendering is active) */
|
||||||
int weight = 0;
|
|
||||||
if(ll1 < ll0)
|
|
||||||
weight -= w1;
|
|
||||||
else if(ll1 > ll0)
|
|
||||||
weight += w1;
|
|
||||||
int ll2 = getLightLevel(skyemit2, true);
|
|
||||||
if(ll2 < ll0)
|
|
||||||
weight -= w2;
|
|
||||||
else if(ll2 > ll0)
|
|
||||||
weight += w2;
|
|
||||||
outcolor[0].setColor(incolor);
|
|
||||||
int cscale = 256;
|
|
||||||
if(weight == 0) {
|
|
||||||
cscale = shadowscale[ll0];
|
|
||||||
}
|
|
||||||
else if(weight < 0) { /* If negative, interpolate down */
|
|
||||||
weight = -weight;
|
|
||||||
if(ll0 > 0) {
|
|
||||||
cscale = (shadowscale[ll0] * (scale-weight) + shadowscale[ll0-1] * weight)/scale;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
cscale = shadowscale[ll0];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
if(ll0 < 15) {
|
|
||||||
cscale = (shadowscale[ll0] * (scale-weight) + shadowscale[ll0+1] * weight)/scale;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
cscale = shadowscale[ll0];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if(cscale < 256) {
|
|
||||||
outcolor[0].scaleRGB(cscale);
|
|
||||||
}
|
|
||||||
if(outcolor.length > 1) {
|
if(outcolor.length > 1) {
|
||||||
ll0 = getLightLevel(skyemit0, false);
|
applySmoothedLightToColor(outcolor[1], incolor, ll0, ll1, ll2, false, w1, w2, scale, shadowscale);
|
||||||
ll1 = getLightLevel(skyemit1, false);
|
|
||||||
weight = 0;
|
|
||||||
if(ll1 < ll0)
|
|
||||||
weight -= w1;
|
|
||||||
else if(ll1 > ll0)
|
|
||||||
weight += w1;
|
|
||||||
ll2 = getLightLevel(skyemit2, false);
|
|
||||||
if(ll2 < ll0)
|
|
||||||
weight -= w2;
|
|
||||||
else if(ll2 > ll0)
|
|
||||||
weight += w2;
|
|
||||||
outcolor[1].setColor(incolor);
|
|
||||||
cscale = 256;
|
|
||||||
if(weight == 0) {
|
|
||||||
cscale = shadowscale[ll0];
|
|
||||||
}
|
|
||||||
else if(weight < 0) { /* If negative, interpolate down */
|
|
||||||
weight = -weight;
|
|
||||||
if(ll0 > 0) {
|
|
||||||
cscale = (shadowscale[ll0] * (scale-weight) + shadowscale[ll0-1] * weight)/scale;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
cscale = shadowscale[ll0];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
if(ll0 < 15) {
|
|
||||||
cscale = (shadowscale[ll0] * (scale-weight) + shadowscale[ll0+1] * weight)/scale;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
cscale = shadowscale[ll0];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if(cscale < 256) {
|
|
||||||
outcolor[1].scaleRGB(cscale);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Apply smooth lighting to a single output color for one pass (ambient or day). */
|
||||||
|
private void applySmoothedLightToColor(Color out, Color incolor,
|
||||||
|
LightLevels ll0, LightLevels ll1, LightLevels ll2,
|
||||||
|
boolean useambient, int w1, int w2, int scale, int[] shadowscale) {
|
||||||
|
int lv0 = getLightLevel(ll0, useambient);
|
||||||
|
int lv1 = getLightLevel(ll1, useambient);
|
||||||
|
int weight = 0;
|
||||||
|
if(lv1 < lv0) weight -= w1;
|
||||||
|
else if(lv1 > lv0) weight += w1;
|
||||||
|
int lv2 = getLightLevel(ll2, useambient);
|
||||||
|
if(lv2 < lv0) weight -= w2;
|
||||||
|
else if(lv2 > lv0) weight += w2;
|
||||||
|
out.setColor(incolor);
|
||||||
|
int cscale = computeSmoothedCscale(lv0, weight, scale, shadowscale);
|
||||||
|
if(cscale < 256) {
|
||||||
|
out.scaleRGB(cscale);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Interpolate the shadow scale for a light level, blending toward the adjacent level by weight/scale. */
|
||||||
|
private int computeSmoothedCscale(int ll0, int weight, int scale, int[] shadowscale) {
|
||||||
|
if(weight == 0) {
|
||||||
|
return shadowscale[ll0];
|
||||||
|
}
|
||||||
|
if(weight < 0) {
|
||||||
|
weight = -weight;
|
||||||
|
return (ll0 > 0)
|
||||||
|
? (shadowscale[ll0] * (scale - weight) + shadowscale[ll0 - 1] * weight) / scale
|
||||||
|
: shadowscale[ll0];
|
||||||
|
}
|
||||||
|
return (ll0 < 15)
|
||||||
|
? (shadowscale[ll0] * (scale - weight) + shadowscale[ll0 + 1] * weight) / scale
|
||||||
|
: shadowscale[ll0];
|
||||||
|
}
|
||||||
|
|
||||||
private final int getLightLevel(final LightLevels ll, boolean useambient) {
|
private final int getLightLevel(final LightLevels ll, boolean useambient) {
|
||||||
int lightlevel;
|
int lightlevel = useambient ? lightscale[ll.sky] : ll.sky;
|
||||||
/* If ambient light, adjust base lighting for it */
|
|
||||||
if(useambient)
|
|
||||||
lightlevel = lightscale[ll.sky];
|
|
||||||
else
|
|
||||||
lightlevel = ll.sky;
|
|
||||||
/* If we're below max, see if emitted light helps */
|
|
||||||
if(lightlevel < 15) {
|
if(lightlevel < 15) {
|
||||||
lightlevel = Math.max(ll.emitted, lightlevel);
|
lightlevel = Math.max(ll.emitted, lightlevel);
|
||||||
}
|
}
|
||||||
return lightlevel;
|
return lightlevel;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Apply lighting to given pixel colors (1 outcolor if normal, 2 if night/day) */
|
/* Apply lighting to given pixel colors (1 outcolor if normal, 2 if night/day) */
|
||||||
public void applyLighting(HDPerspectiveState ps, HDShaderState ss, Color incolor, Color[] outcolor) {
|
public void applyLighting(HDPerspectiveState ps, HDShaderState ss, Color incolor, Color[] outcolor) {
|
||||||
int[] shadowscale = null;
|
int[] shadowscale = ss.getLightingTable();
|
||||||
if (smooth && ps.getShade()) {
|
if(shadowscale == null) {
|
||||||
shadowscale = ss.getLightingTable();
|
shadowscale = defLightingTable;
|
||||||
if (shadowscale == null) {
|
}
|
||||||
shadowscale = defLightingTable;
|
if(smooth && ps.getShade()) {
|
||||||
}
|
|
||||||
applySmoothLighting(ps, ss, incolor, outcolor, shadowscale);
|
applySmoothLighting(ps, ss, incolor, outcolor, shadowscale);
|
||||||
checkGrayscale(outcolor);
|
checkGrayscale(outcolor);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
LightLevels ll = null;
|
/* Non-smooth: fetch light levels and apply flat shadow */
|
||||||
int lightlevel = 15, lightlevel_day = 15;
|
LightLevels ll = ps.getCachedLightLevels(0);
|
||||||
/* If processing for shadows, use sky light level as base lighting */
|
ps.getLightLevels(ll);
|
||||||
if(defLightingTable != null) {
|
int lightlevel = lightscale[ll.sky]; // apply ambient scale immediately
|
||||||
shadowscale = ss.getLightingTable();
|
int lightlevel_day = ll.sky;
|
||||||
if (shadowscale == null) {
|
|
||||||
shadowscale = defLightingTable;
|
|
||||||
}
|
|
||||||
ll = ps.getCachedLightLevels(0);
|
|
||||||
ps.getLightLevels(ll);
|
|
||||||
lightlevel = lightlevel_day = ll.sky;
|
|
||||||
}
|
|
||||||
/* If ambient light, adjust base lighting for it */
|
|
||||||
lightlevel = lightscale[lightlevel];
|
|
||||||
/* If we're below max, see if emitted light helps */
|
|
||||||
if((lightlevel < 15) || (lightlevel_day < 15)) {
|
if((lightlevel < 15) || (lightlevel_day < 15)) {
|
||||||
int emitted = ll.emitted;
|
int emitted = ll.emitted;
|
||||||
lightlevel = Math.max(emitted, lightlevel);
|
lightlevel = Math.max(emitted, lightlevel);
|
||||||
lightlevel_day = Math.max(emitted, lightlevel_day);
|
lightlevel_day = Math.max(emitted, lightlevel_day);
|
||||||
}
|
}
|
||||||
/* Figure out our color, with lighting if needed */
|
|
||||||
outcolor[0].setColor(incolor);
|
outcolor[0].setColor(incolor);
|
||||||
if(lightlevel < 15) {
|
if(lightlevel < 15) {
|
||||||
shadowColor(outcolor[0], lightlevel, shadowscale);
|
int s = shadowscale[lightlevel];
|
||||||
|
if(s < 256) outcolor[0].scaleRGB(s);
|
||||||
}
|
}
|
||||||
if(outcolor.length > 1) {
|
if(outcolor.length > 1) {
|
||||||
if(lightlevel_day == lightlevel) {
|
if(lightlevel_day == lightlevel) {
|
||||||
|
|
@ -255,19 +166,14 @@ public class ShadowHDLighting extends DefaultHDLighting {
|
||||||
else {
|
else {
|
||||||
outcolor[1].setColor(incolor);
|
outcolor[1].setColor(incolor);
|
||||||
if(lightlevel_day < 15) {
|
if(lightlevel_day < 15) {
|
||||||
shadowColor(outcolor[1], lightlevel_day, shadowscale);
|
int s = shadowscale[lightlevel_day];
|
||||||
|
if(s < 256) outcolor[1].scaleRGB(s);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
checkGrayscale(outcolor);
|
checkGrayscale(outcolor);
|
||||||
}
|
}
|
||||||
|
|
||||||
private final void shadowColor(Color c, int lightlevel, int[] shadowscale) {
|
|
||||||
int scale = shadowscale[lightlevel];
|
|
||||||
if(scale < 256)
|
|
||||||
c.scaleRGB(scale);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Test if night/day is enabled for this renderer */
|
/* Test if night/day is enabled for this renderer */
|
||||||
public boolean isNightAndDayEnabled() { return night_and_day; }
|
public boolean isNightAndDayEnabled() { return night_and_day; }
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue