using UnityEngine;
using System.Collections;
using System.Collections.Generic;
namespace WorldStreamer2
{
///
/// Sets Terrain neighbours.
///
public class TerrainNeighbours : MonoBehaviour
{
public List terrainsToOmit;
[Tooltip("If you use Floating Point fix system drag and drop world mover prefab from your scene hierarchy.")]
///
/// The world mover.
///
public WorldMover worldMover;
public List _terrains = new List();
Dictionary _terrainDict = null;
[Tooltip("Debug value, it gives info about starting position offset.")]
///
/// The first position for terrain tile management.
///
Vector2 firstPosition;
int sizeX = 0;
int sizeZ = 0;
bool firstPositonSet = false;
///
/// Start this instance and creates neighbours for scene terrains
///
void Start()
{
CreateNeighbours();
}
///
/// Sets the neighbours for all terrains in scenes
///
public void CreateNeighbours()
{
//https://github.com/Unity-Technologies/UnityCsReference/blob/02d565cf3dd0f6b15069ba976064c75dc2705b08/Modules/Terrain/Public/TerrainUtility.cs
//UnityEngine.Experimental.TerrainAPI.TerrainUtility.AutoConnect();
//return;
List _terrainsNew = new List();
_terrainsNew.AddRange(Terrain.activeTerrains);
foreach (var item in terrainsToOmit)
{
if (_terrainsNew.Contains(item))
{
_terrainsNew.Remove(item);
}
}
foreach (var item in _terrains)
{
if (_terrainsNew.Contains(item))
{
_terrainsNew.Remove(item);
}
}
if (_terrainDict == null)
_terrainDict = new Dictionary(new IntArrayComparer());
Dictionary _terrainDictNew = new Dictionary(new IntArrayComparer());
Dictionary _terrainDictRob2 = new Dictionary(new IntArrayComparer());
if (_terrainsNew.Count > 0)
{
if (!firstPositonSet)
{
firstPositonSet = true;
firstPosition = new Vector2(_terrainsNew[0].transform.position.x, _terrainsNew[0].transform.position.z);
sizeX = (int)_terrainsNew[0].terrainData.size.x;
sizeZ = (int)_terrainsNew[0].terrainData.size.z;
}
foreach (var terrain in _terrainsNew)
{
_terrains.Add(terrain);
Vector3 pos = terrain.transform.position;
if (worldMover != null)
pos -= worldMover.currentMove;
int[] posTer = new int[] {
(int)(Mathf.RoundToInt ((pos.x - firstPosition.x) / sizeX)),
(int)(Mathf.RoundToInt ((pos.z - firstPosition.y) / sizeZ))
};
if (_terrainDict.ContainsKey(posTer))
{
_terrainDict[posTer] = terrain;
}
else
_terrainDict.Add(posTer, terrain);
_terrainDictNew.Add(posTer, terrain);
}
foreach (var item in _terrainDictNew)
{
int[] posTer = item.Key;
Terrain top = null;
Terrain left = null;
Terrain right = null;
Terrain bottom = null;
int[] topPos = new int[] {
posTer [0],
posTer [1] + 1
};
_terrainDict.TryGetValue(topPos, out top);
int[] leftPos = new int[] {
posTer [0] - 1,
posTer [1]
};
_terrainDict.TryGetValue(leftPos, out left);
int[] posRight = new int[] {
posTer [0] + 1,
posTer [1]
};
_terrainDict.TryGetValue(posRight, out right);
int[] posBottom = new int[] {
posTer [0],
posTer [1] - 1
};
_terrainDict.TryGetValue(posBottom, out bottom);
item.Value.SetNeighbors(left, top, right, bottom);
item.Value.Flush();
if (top != null && !_terrainDictRob2.ContainsKey(topPos))
_terrainDictRob2.Add(topPos, top);
if (left != null && !_terrainDictRob2.ContainsKey(leftPos))
_terrainDictRob2.Add(leftPos, left);
if (right != null && !_terrainDictRob2.ContainsKey(posRight))
_terrainDictRob2.Add(posRight, right);
if (bottom != null && !_terrainDictRob2.ContainsKey(posBottom))
_terrainDictRob2.Add(posBottom, bottom);
}
foreach (var item in _terrainDictRob2)
{
int[] posTer = item.Key;
Terrain top = null;
Terrain left = null;
Terrain right = null;
Terrain bottom = null;
int[] topPos = new int[] {
posTer [0],
posTer [1] + 1
};
_terrainDict.TryGetValue(topPos, out top);
int[] leftPos = new int[] {
posTer [0] - 1,
posTer [1]
};
_terrainDict.TryGetValue(leftPos, out left);
int[] posRight = new int[] {
posTer [0] + 1,
posTer [1]
};
_terrainDict.TryGetValue(posRight, out right);
int[] posBottom = new int[] {
posTer [0],
posTer [1] - 1
};
_terrainDict.TryGetValue(posBottom, out bottom);
item.Value.SetNeighbors(left, top, right, bottom);
item.Value.Flush();
}
// Terrain.SetConnectivityDirty();
}
}
}
}