* Patch from jhurliman - Implements a binary search in the LLRAW exporter which dramatically speeds up exports.
parent
ed717ec181
commit
de06c85259
|
@ -33,6 +33,40 @@ namespace OpenSim.Region.Environment.Modules.World.Terrain.FileLoaders
|
||||||
{
|
{
|
||||||
public class LLRAW : ITerrainLoader
|
public class LLRAW : ITerrainLoader
|
||||||
{
|
{
|
||||||
|
public struct HeightmapLookupValue : IComparable<HeightmapLookupValue>
|
||||||
|
{
|
||||||
|
public int Index;
|
||||||
|
public double Value;
|
||||||
|
|
||||||
|
public HeightmapLookupValue(int index, double value)
|
||||||
|
{
|
||||||
|
Index = index;
|
||||||
|
Value = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int CompareTo(HeightmapLookupValue val)
|
||||||
|
{
|
||||||
|
return Value.CompareTo(val.Value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>Lookup table to speed up terrain exports</summary>
|
||||||
|
HeightmapLookupValue[] LookupHeightTable;
|
||||||
|
|
||||||
|
public LLRAW()
|
||||||
|
{
|
||||||
|
LookupHeightTable = new HeightmapLookupValue[256 * 256];
|
||||||
|
|
||||||
|
for (int i = 0; i < 256; i++)
|
||||||
|
{
|
||||||
|
for (int j = 0; j < 256; j++)
|
||||||
|
{
|
||||||
|
LookupHeightTable[i + (j * 256)] = new HeightmapLookupValue(i + (j * 256), ((double)i * ((double)j / 127.0d)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Array.Sort<HeightmapLookupValue>(LookupHeightTable);
|
||||||
|
}
|
||||||
|
|
||||||
#region ITerrainLoader Members
|
#region ITerrainLoader Members
|
||||||
|
|
||||||
public ITerrainChannel LoadFile(string filename)
|
public ITerrainChannel LoadFile(string filename)
|
||||||
|
@ -70,37 +104,21 @@ namespace OpenSim.Region.Environment.Modules.World.Terrain.FileLoaders
|
||||||
FileStream s = file.Open(FileMode.CreateNew, FileAccess.Write);
|
FileStream s = file.Open(FileMode.CreateNew, FileAccess.Write);
|
||||||
BinaryWriter binStream = new BinaryWriter(s);
|
BinaryWriter binStream = new BinaryWriter(s);
|
||||||
|
|
||||||
// Generate a smegging big lookup table to speed the operation up (it needs it)
|
|
||||||
double[] lookupHeightTable = new double[65536];
|
|
||||||
int i;
|
|
||||||
int y;
|
|
||||||
for (i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
int j;
|
|
||||||
for (j = 0; j < 256; j++)
|
|
||||||
{
|
|
||||||
lookupHeightTable[i + (j * 256)] = (i * (j / 127.0));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Output the calculated raw
|
// Output the calculated raw
|
||||||
for (y = 0; y < map.Height; y++)
|
for (int y = 0; y < map.Height; y++)
|
||||||
{
|
{
|
||||||
int x;
|
for (int x = 0; x < map.Width; x++)
|
||||||
for (x = 0; x < map.Width; x++)
|
|
||||||
{
|
{
|
||||||
double t = map[x, y];
|
double t = map[x, y];
|
||||||
double min = double.MaxValue;
|
|
||||||
int index = 0;
|
int index = 0;
|
||||||
|
|
||||||
for (i = 0; i < 65536; i++)
|
// The lookup table is pre-sorted, so we either find an exact match or
|
||||||
{
|
// the next closest (smaller) match with a binary search
|
||||||
if (Math.Abs(t - lookupHeightTable[i]) < min)
|
index = Array.BinarySearch<HeightmapLookupValue>(LookupHeightTable, new HeightmapLookupValue(0, t));
|
||||||
{
|
if (index < 0)
|
||||||
min = Math.Abs(t - lookupHeightTable[i]);
|
index = ~index - 1;
|
||||||
index = i;
|
|
||||||
}
|
index = LookupHeightTable[index].Index;
|
||||||
}
|
|
||||||
|
|
||||||
byte red = (byte) (index & 0xFF);
|
byte red = (byte) (index & 0xFF);
|
||||||
byte green = (byte) ((index >> 8) & 0xFF);
|
byte green = (byte) ((index >> 8) & 0xFF);
|
||||||
|
@ -149,4 +167,4 @@ namespace OpenSim.Region.Environment.Modules.World.Terrain.FileLoaders
|
||||||
return "LL/SL RAW";
|
return "LL/SL RAW";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue