mirror of
https://github.com/opensim/opensim.git
synced 2026-08-07 01:35:46 +08:00
Major ass changes to terrain (now uses libTerrain-BSD!) and all-round improvements to code quality. Terrain saving/loading may work now (running through setHeights1D and getHeights1D before DB4o) **WARNING: UNTESTED**
This commit is contained in:
@@ -39,8 +39,8 @@ namespace OpenSim.Framework.Interfaces
|
||||
void StorePrim(PrimData prim);
|
||||
void RemovePrim(LLUUID primID);
|
||||
void LoadPrimitives(ILocalStorageReceiver receiver);
|
||||
float[,] LoadWorld();
|
||||
void SaveMap(float[,] heightmap);
|
||||
float[] LoadWorld();
|
||||
void SaveMap(float[] heightmap);
|
||||
void ShutDown();
|
||||
}
|
||||
|
||||
|
||||
@@ -44,7 +44,7 @@ namespace OpenSim.world
|
||||
OpenSim.Framework.Console.MainConsole.Instance.WriteLine("Avatar.cs - Loading details from grid (DUMMY)");
|
||||
ControllingClient = TheClient;
|
||||
localid = 8880000 + (this.m_world._localNumber++);
|
||||
Pos = new LLVector3(100.0f, 100.0f, m_world.Terrain.map[(int)Pos.X, (int)Pos.Y] + 1.0f);
|
||||
Pos = new LLVector3(100.0f, 100.0f, m_world.Terrain[(int)Pos.X, (int)Pos.Y] + 1.0f);
|
||||
visualParams = new byte[218];
|
||||
for (int i = 0; i < 218; i++)
|
||||
{
|
||||
@@ -332,7 +332,7 @@ namespace OpenSim.world
|
||||
|
||||
public override void LandRenegerated()
|
||||
{
|
||||
Pos = new LLVector3(100.0f, 100.0f, m_world.Terrain.map[(int)Pos.X, (int)Pos.Y] + 50.0f);
|
||||
Pos = new LLVector3(100.0f, 100.0f, m_world.Terrain[(int)Pos.X, (int)Pos.Y] + 50.0f);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -198,7 +198,7 @@ namespace OpenSim.world
|
||||
{
|
||||
this.phyScene.SetTerrain(Terrain.getHeights1D());
|
||||
}
|
||||
this.localStorage.SaveMap(this.Terrain.map);
|
||||
this.localStorage.SaveMap(this.Terrain.getHeights1D());
|
||||
|
||||
foreach (SimClient client in m_clientThreads.Values)
|
||||
{
|
||||
@@ -213,12 +213,12 @@ namespace OpenSim.world
|
||||
|
||||
public void RegenerateTerrain(float[,] newMap)
|
||||
{
|
||||
this.Terrain.map = newMap;
|
||||
this.Terrain.setHeights2D(newMap);
|
||||
lock (this.LockPhysicsEngine)
|
||||
{
|
||||
this.phyScene.SetTerrain(this.Terrain.getHeights1D());
|
||||
}
|
||||
this.localStorage.SaveMap(this.Terrain.map);
|
||||
this.localStorage.SaveMap(this.Terrain.getHeights1D());
|
||||
|
||||
foreach (SimClient client in m_clientThreads.Values)
|
||||
{
|
||||
@@ -239,7 +239,7 @@ namespace OpenSim.world
|
||||
{
|
||||
this.phyScene.SetTerrain(this.Terrain.getHeights1D());
|
||||
}
|
||||
this.localStorage.SaveMap(this.Terrain.map);
|
||||
this.localStorage.SaveMap(this.Terrain.getHeights1D());
|
||||
|
||||
foreach (SimClient client in m_clientThreads.Values)
|
||||
{
|
||||
@@ -252,7 +252,7 @@ namespace OpenSim.world
|
||||
|
||||
public void LoadWorldMap()
|
||||
{
|
||||
float[,] map = this.localStorage.LoadWorld();
|
||||
float[] map = this.localStorage.LoadWorld();
|
||||
if (map == null)
|
||||
{
|
||||
this.Terrain.hills();
|
||||
@@ -260,7 +260,7 @@ namespace OpenSim.world
|
||||
}
|
||||
else
|
||||
{
|
||||
this.Terrain.map = map;
|
||||
this.Terrain.setHeights1D(map);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -118,11 +118,11 @@ namespace OpenSim.Storage.LocalStorageDb4o
|
||||
}
|
||||
}
|
||||
|
||||
public float[,] LoadWorld()
|
||||
public float[] LoadWorld()
|
||||
{
|
||||
OpenSim.Framework.Console.MainConsole.Instance.WriteLine("LoadWorld() - Loading world....");
|
||||
//World blank = new World();
|
||||
float[,] heightmap = null;
|
||||
float[] heightmap = null;
|
||||
OpenSim.Framework.Console.MainConsole.Instance.WriteLine("LoadWorld() - Looking for a heightmap in local DB");
|
||||
IObjectSet world_result = db.Get(typeof(MapStorage));
|
||||
if (world_result.Count > 0)
|
||||
@@ -150,7 +150,7 @@ namespace OpenSim.Storage.LocalStorageDb4o
|
||||
return heightmap;
|
||||
}
|
||||
|
||||
public void SaveMap(float[,] heightmap)
|
||||
public void SaveMap(float[] heightmap)
|
||||
{
|
||||
IObjectSet world_result = db.Get(typeof(MapStorage));
|
||||
if (world_result.Count > 0)
|
||||
|
||||
@@ -6,7 +6,7 @@ namespace OpenSim.Storage.LocalStorageDb4o
|
||||
{
|
||||
public class MapStorage
|
||||
{
|
||||
public float[,] Map;
|
||||
public float[] Map;
|
||||
|
||||
public MapStorage()
|
||||
{
|
||||
|
||||
@@ -1,72 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace OpenSim.Terrain.BasicTerrain
|
||||
{
|
||||
static class Hills
|
||||
{
|
||||
/// <summary>
|
||||
/// Generates a series of spheres which are then either max()'d or added together. Inspired by suggestion from jh.
|
||||
/// </summary>
|
||||
/// <remarks>3-Clause BSD Licensed</remarks>
|
||||
/// <param name="number">The number of hills to generate</param>
|
||||
/// <param name="scale_min">The minimum size of each hill</param>
|
||||
/// <param name="scale_range">The maximum size of each hill</param>
|
||||
/// <param name="island">Whether to bias hills towards the center of the map</param>
|
||||
/// <param name="additive">Whether to add hills together or to pick the largest value</param>
|
||||
/// <param name="noisy">Generates hill-shaped noise instead of consistent hills</param>
|
||||
public static void hillsSpheres(float[,] map,int seed, int number, double scale_min, double scale_range, bool island, bool additive, bool noisy)
|
||||
{
|
||||
Random random = new Random(seed);
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
int x, y;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < number; i++)
|
||||
{
|
||||
double rx = Math.Min(255.0, random.NextDouble() * w);
|
||||
double ry = Math.Min(255.0, random.NextDouble() * h);
|
||||
double rand = random.NextDouble();
|
||||
|
||||
if (island)
|
||||
{
|
||||
// Move everything towards the center
|
||||
rx -= w / 2;
|
||||
rx /= 2;
|
||||
rx += w / 2;
|
||||
|
||||
ry -= h / 2;
|
||||
ry /= 2;
|
||||
ry += h / 2;
|
||||
}
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
if (noisy)
|
||||
rand = random.NextDouble();
|
||||
|
||||
double z = (scale_min + (scale_range * rand));
|
||||
z *= z;
|
||||
z -= ((x - rx) * (x - rx)) + ((y - ry) * (y - ry));
|
||||
|
||||
if (z < 0)
|
||||
z = 0;
|
||||
|
||||
if (additive)
|
||||
{
|
||||
map[x, y] += (float)z;
|
||||
}
|
||||
else
|
||||
{
|
||||
map[x, y] = (float)Math.Max(map[x, y], z);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,102 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace OpenSim.Terrain.BasicTerrain
|
||||
{
|
||||
static class Normalise
|
||||
{
|
||||
/// <summary>
|
||||
/// Converts the heightmap to values ranging from 0..1
|
||||
/// </summary>
|
||||
/// <param name="map">The heightmap to be normalised</param>
|
||||
public static void normalise(float[,] map)
|
||||
{
|
||||
double max = findMax(map);
|
||||
double min = findMin(map);
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
|
||||
int x, y;
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
map[x, y] = (float)((map[x, y] - min) * (1.0 / (max - min)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Converts the heightmap to values ranging from 0..<newmax>
|
||||
/// </summary>
|
||||
/// <param name="map">The heightmap to be normalised</param>
|
||||
/// <param name="newmax">The new maximum height value of the map</param>
|
||||
public static void normalise(float[,] map, double newmax)
|
||||
{
|
||||
double max = findMax(map);
|
||||
double min = findMin(map);
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
|
||||
int x, y;
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
map[x, y] = (float)((map[x, y] - min) * (1.0 / (max - min)) * newmax);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Finds the largest value in the heightmap
|
||||
/// </summary>
|
||||
/// <param name="map">The heightmap</param>
|
||||
/// <returns>The highest value</returns>
|
||||
public static double findMax(float[,] map)
|
||||
{
|
||||
int x, y;
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
double max = double.MinValue;
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
if (map[x, y] > max)
|
||||
max = map[x, y];
|
||||
}
|
||||
}
|
||||
|
||||
return max;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Finds the lowest value in a heightmap
|
||||
/// </summary>
|
||||
/// <param name="map">The heightmap</param>
|
||||
/// <returns>The minimum value</returns>
|
||||
public static double findMin(float[,] map)
|
||||
{
|
||||
int x, y;
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
double min = double.MaxValue;
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
if (map[x, y] < min)
|
||||
min = map[x, y];
|
||||
}
|
||||
}
|
||||
|
||||
return min;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -28,14 +28,12 @@
|
||||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="libTerrain-BSD, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL" />
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Data" />
|
||||
<Reference Include="System.Xml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="Hills.cs" />
|
||||
<Compile Include="Normalise.cs" />
|
||||
<Compile Include="RaiseLower.cs" />
|
||||
<Compile Include="TerrainEngine.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
</ItemGroup>
|
||||
|
||||
@@ -1,91 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace OpenSim.Terrain.BasicTerrain
|
||||
{
|
||||
static class RaiseLower
|
||||
{
|
||||
/// <summary>
|
||||
/// Raises land around the selection
|
||||
/// </summary>
|
||||
/// <param name="rx">The center the X coordinate of where you wish to raise the land</param>
|
||||
/// <param name="ry">The center the Y coordinate of where you wish to raise the land</param>
|
||||
/// <param name="size">The radius of the dimple</param>
|
||||
/// <param name="amount">How much impact to add to the terrain (0..2 usually)</param>
|
||||
public static void raise(float[,] map, double rx, double ry, double size, double amount)
|
||||
{
|
||||
raiseSphere(map, rx, ry, size, amount);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Raises land in a sphere around the selection
|
||||
/// </summary>
|
||||
/// <param name="rx">The center the X coordinate of where you wish to raise the land</param>
|
||||
/// <param name="ry">The center the Y coordinate of where you wish to raise the land</param>
|
||||
/// <param name="size">The radius of the sphere dimple</param>
|
||||
/// <param name="amount">How much impact to add to the terrain (0..2 usually)</param>
|
||||
public static void raiseSphere(float[,] map, double rx, double ry, double size, double amount)
|
||||
{
|
||||
int x, y;
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
double z = size;
|
||||
z *= z;
|
||||
z -= ((x - rx) * (x - rx)) + ((y - ry) * (y - ry));
|
||||
|
||||
if (z < 0)
|
||||
z = 0;
|
||||
|
||||
map[x, y] += (float)(z * amount);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Lowers land in a sphere around the selection
|
||||
/// </summary>
|
||||
/// <param name="rx">The center the X coordinate of where you wish to lower the land</param>
|
||||
/// <param name="ry">The center the Y coordinate of where you wish to lower the land</param>
|
||||
/// <param name="size">The radius of the sphere dimple</param>
|
||||
/// <param name="amount">How much impact to remove from the terrain (0..2 usually)</param>
|
||||
public static void lower(float[,] map, double rx, double ry, double size, double amount)
|
||||
{
|
||||
lowerSphere(map, rx, ry, size, amount);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Lowers land in a sphere around the selection
|
||||
/// </summary>
|
||||
/// <param name="rx">The center the X coordinate of where you wish to lower the land</param>
|
||||
/// <param name="ry">The center the Y coordinate of where you wish to lower the land</param>
|
||||
/// <param name="size">The radius of the sphere dimple</param>
|
||||
/// <param name="amount">How much impact to remove from the terrain (0..2 usually)</param>
|
||||
public static void lowerSphere(float[,] map, double rx, double ry, double size, double amount)
|
||||
{
|
||||
int x, y;
|
||||
int w = map.GetLength(0);
|
||||
int h = map.GetLength(1);
|
||||
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
double z = size;
|
||||
z *= z;
|
||||
z -= ((x - rx) * (x - rx)) + ((y - ry) * (y - ry));
|
||||
|
||||
if (z < 0)
|
||||
z = 0;
|
||||
|
||||
map[x, y] -= (float)(z * amount);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,7 +1,7 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using OpenSim.Terrain.BasicTerrain;
|
||||
using libTerrain;
|
||||
|
||||
namespace OpenSim.Terrain
|
||||
{
|
||||
@@ -10,11 +10,8 @@ namespace OpenSim.Terrain
|
||||
/// <summary>
|
||||
/// A [normally] 256x256 heightmap
|
||||
/// </summary>
|
||||
public float[,] map;
|
||||
/// <summary>
|
||||
/// A 256x256 heightmap storing water height values
|
||||
/// </summary>
|
||||
public float[,] water;
|
||||
public Channel heightmap;
|
||||
|
||||
int w, h;
|
||||
|
||||
/// <summary>
|
||||
@@ -24,8 +21,7 @@ namespace OpenSim.Terrain
|
||||
{
|
||||
w = 256;
|
||||
h = 256;
|
||||
map = new float[w, h];
|
||||
water = new float[w, h];
|
||||
heightmap = new Channel(w, h);
|
||||
|
||||
}
|
||||
|
||||
@@ -38,7 +34,21 @@ namespace OpenSim.Terrain
|
||||
float[] heights = new float[w*h];
|
||||
int i;
|
||||
for(i=0;i<w*h;i++) {
|
||||
heights[i] = map[i / w, i % w];
|
||||
heights[i] = (float)heightmap.map[i / w, i % w];
|
||||
}
|
||||
return heights;
|
||||
}
|
||||
|
||||
public float[,] getHeights2D()
|
||||
{
|
||||
float[,] heights = new float[w, h];
|
||||
int x, y;
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
heights[x, y] = (float)heightmap.map[x, y];
|
||||
}
|
||||
}
|
||||
return heights;
|
||||
}
|
||||
@@ -52,13 +62,27 @@ namespace OpenSim.Terrain
|
||||
int i;
|
||||
for (i = 0; i < w * h; i++)
|
||||
{
|
||||
map[i / w, i % w] = heights[i];
|
||||
heightmap.map[i / w, i % w] = heights[i];
|
||||
}
|
||||
}
|
||||
|
||||
public float[,] setHeights2D(float[,] heights)
|
||||
{
|
||||
int x, y;
|
||||
for (x = 0; x < w; x++)
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
heightmap.set(x,y,(double)heights[x,y]);
|
||||
}
|
||||
}
|
||||
return heights;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Loads a file consisting of 256x256 doubles and imports it as an array into the map.
|
||||
/// </summary>
|
||||
/// <remarks>TODO: Move this to libTerrain itself</remarks>
|
||||
/// <param name="filename">The filename of the double array to import</param>
|
||||
public void loadFromFileF64(string filename)
|
||||
{
|
||||
@@ -70,21 +94,11 @@ namespace OpenSim.Terrain
|
||||
{
|
||||
for (y = 0; y < h; y++)
|
||||
{
|
||||
map[x, y] = (float)bs.ReadDouble();
|
||||
heightmap.map[x, y] = bs.ReadDouble();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Swaps the references between the height and water buffers to allow you to edit the water heightmap. Remember to swap back when you are done.
|
||||
/// </summary>
|
||||
public void swapWaterBuffer()
|
||||
{
|
||||
float[,] temp = map;
|
||||
map = water;
|
||||
water = temp;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Raises land in a sphere around the specified coordinates
|
||||
/// </summary>
|
||||
@@ -94,9 +108,9 @@ namespace OpenSim.Terrain
|
||||
/// <param name="amount">Scale the height of the sphere by this amount (recommended 0..2)</param>
|
||||
public void raise(double rx, double ry, double size, double amount)
|
||||
{
|
||||
lock (map)
|
||||
lock (heightmap)
|
||||
{
|
||||
RaiseLower.raiseSphere(this.map, rx, ry, size, amount);
|
||||
heightmap.raise(rx, ry, size, amount);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -109,9 +123,9 @@ namespace OpenSim.Terrain
|
||||
/// <param name="amount">Scale the height of the sphere by this amount (recommended 0..2)</param>
|
||||
public void lower(double rx, double ry, double size, double amount)
|
||||
{
|
||||
lock (map)
|
||||
lock (heightmap)
|
||||
{
|
||||
RaiseLower.lowerSphere(this.map, rx, ry, size, amount);
|
||||
heightmap.lower(rx, ry, size, amount);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -120,12 +134,24 @@ namespace OpenSim.Terrain
|
||||
/// </summary>
|
||||
public void hills()
|
||||
{
|
||||
lock (map)
|
||||
lock (heightmap)
|
||||
{
|
||||
Hills.hillsSpheres(this.map, 1337, 200, 20, 40, true, true, false);
|
||||
Normalise.normalise(this.map,60);
|
||||
heightmap.hillsSpheres(200, 20, 40, true, true, false);
|
||||
heightmap.normalise();
|
||||
heightmap *= 60.0; // Raise to 60m
|
||||
}
|
||||
}
|
||||
|
||||
public float this[int x, int y]
|
||||
{
|
||||
get
|
||||
{
|
||||
return (float)heightmap.get(x,y);
|
||||
}
|
||||
set
|
||||
{
|
||||
heightmap.set(x,y,(double)value);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Binary file not shown.
Binary file not shown.
BIN
OpenSim.Terrain.BasicTerrain/bin/Debug/libTerrain-BSD.dll
Normal file
BIN
OpenSim.Terrain.BasicTerrain/bin/Debug/libTerrain-BSD.dll
Normal file
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
bin/libTerrain-BSD.dll
Normal file
BIN
bin/libTerrain-BSD.dll
Normal file
Binary file not shown.
@@ -379,6 +379,7 @@
|
||||
</Configuration>
|
||||
|
||||
<ReferencePath>../bin/</ReferencePath>
|
||||
<Reference name="libTerrain-BSD.dll"/>
|
||||
<Reference name="System"/>
|
||||
<Reference name="System.Data"/>
|
||||
<Reference name="System.Xml"/>
|
||||
|
||||
Reference in New Issue
Block a user