- Home /
Terrain streaming doesn't work. HEEELP!!!
Hi, I'm making a terrain streaming thingy that reads in 16 bit RAW terrains at a LOD dependant on the distance between the camera and the terrain position. I have to split the terrain into multiple pieces for two reasons:
1.Unity limits the number of vertices in a mesh to 65000.
2.Each piece can have a separate LOD level.
It was working when I only had one piece and set the MeshFilter to the mesh, but when I create multiple GameObjects (actually there are 32*32 of them) nothing comes up. The MeshFilters and MeshRendered are added to the GameObjects, but when I transform the GameObjects (in code) and click on them in the hierachy while playing, they are not transformed.
Here is the code for the multi piece terrain streaming thingy.
using UnityEngine;
using System.IO;
using System;
class advancedTerrain : MonoBehaviour
{
public string path;
public int terrainSize;
public int tileSize;
public int[] minLodDistances;
public int[] maxLodDistances;
private int[,] lod;
private int[,] prevLod;
private GameObject[,] gameObjects;
void load(int x, int y)
{
FileStream fileStream = new FileStream(path, FileMode.Open);
byte[] bytes = new byte[2];
Vector3[] vertices = new Vector3[tileSize * tileSize];
int[] triangles = new int[(tileSize * tileSize) * 6];
for (int yy = y * tileSize; yy < (y + 1) * tileSize; yy += lod[y, x])
{
for (int xx = x * tileSize; xx < (x + 1) * tileSize; xx += lod[y, x])
{
fileStream.Position = (yy * terrainSize) + xx;
fileStream.Read(bytes, 0, 2);
vertices[((yy - (y * tileSize)) * tileSize) + (xx - (x * tileSize))] = new Vector3((x * tileSize) + xx, BitConverter.ToInt16(bytes, 0), (y * tileSize) + yy);
if (xx < ((x + 1) * tileSize) - 1 && yy < ((y + 1) * tileSize) - 1)
{
triangles[(((yy - (y * tileSize)) * tileSize) + (xx - (x * tileSize))) * 6] = ((yy - (y * tileSize)) * tileSize) + (xx - (x * tileSize));
triangles[((((yy - (y * tileSize)) * tileSize) + (xx - (x * tileSize))) * 6) + 1] = (((yy + 1) - (y * tileSize)) * tileSize) + (xx - (x * tileSize));
triangles[((((yy - (y * tileSize)) * tileSize) + (xx - (x * tileSize))) * 6) + 2] = ((yy - (y * tileSize)) * tileSize) + ((xx + 1) - (x * tileSize));
}
}
}
Mesh mesh = new Mesh();
mesh.vertices = vertices;
mesh.triangles = triangles;
gameObjects[y, x].GetComponent<MeshFilter>().mesh = mesh;
gameObjects[y, x].transform.position = new Vector3(transform.position.x + (x * tileSize), transform.position.y, transform.position.z + (y * tileSize));
fileStream.Close();
}
void Start()
{
lod = new int[terrainSize / tileSize, terrainSize / tileSize];
prevLod = new int[terrainSize / tileSize, terrainSize / tileSize];
gameObjects = new GameObject[terrainSize / tileSize, terrainSize / tileSize];
for (int y = 0; y < terrainSize / tileSize; y++)
{
for (int x = 0; x < terrainSize / tileSize; x++)
{
lod[y, x] = 1;
prevLod[y, x] = 0;
gameObjects[y, x] = new GameObject();
gameObjects[y, x].AddComponent<MeshFilter>();
gameObjects[y, x].AddComponent<MeshRenderer>();
}
}
}
void Update()
{
for (int y = 0; y < terrainSize / tileSize; y++)
{
for (int x = 0; x < terrainSize / tileSize; x++)
{
double distance = Vector3.Distance(Camera.main.transform.position, new Vector3(transform.position.x + (x * tileSize), transform.position.y, transform.position.z + (y * tileSize)));
for (int a = 0; a < minLodDistances.Length; a++)
{
if (distance >= minLodDistances[a] && distance <= maxLodDistances[a])
{
lod[y, x] = a;
if (prevLod[y, x] != a)
{
prevLod[y, x] = a;
load(x, y);
}
}
}
}
}
}
}
Here is the code for the single piece terrain. Max terrain size is limited to 128 coz 256^2 > 65000
//WARNING!!! THE FOLLOWING CODE SAMPLE IS DEPRECATED!
//ALL PRACTICIONERS OF THE FOLLOWING DEVICE SHALL BE
//PROSECUTED WITHOUT REGARD AND/OR WITH DISREGARD TO
//LOCAL/INTERNATIONAL PEACE AND HARMONY LAWS/RULE BY
//MEMBERS OF THE FEDERAL TORTURE BINARY TWINS!!! :(
using UnityEngine;
using System.IO;
using System;
class advancedTerrain : MonoBehaviour
{
public string path;
public int size;
public float depth;
public int[] minLodDistances;
public int[] maxLodDistances;
private int lod = 1;
private int prevLod = 0;
void load()
{
FileStream fileStream = new FileStream(path, FileMode.Open);
byte[] bytes = new byte[2];
Vector3[] vertices = new Vector3[(size / lod) * (size / lod)];
int[] triangles = new int[((size / lod) * (size / lod)) * 6];
for (int x = 0; x < size / lod; x++)
{
for (int y = 0; y < size / lod; y++)
{
fileStream.Position = (((y * lod) * size) + (x * lod)) * 2;
fileStream.Read(bytes, 0, 2);
vertices[(y * (size / lod)) + x] = new Vector3(x * lod, BitConverter.ToInt16(bytes, 0) * depth, y * lod);
if (x < (size / lod) - 1 && y < (size / lod) - 1)
{
triangles[((y * (size / lod)) + x) * 6] = (y * (size / lod)) + x;
triangles[(((y * (size / lod)) + x) * 6) + 1] = ((y + 1) * (size / lod)) + x;
triangles[(((y * (size / lod)) + x) * 6) + 2] = (y * (size / lod)) + (x + 1);
triangles[(((y * (size / lod)) + x) * 6) + 3] = (y * (size / lod)) + (x + 1);
triangles[(((y * (size / lod)) + x) * 6) + 4] = ((y + 1) * (size / lod)) + x;
triangles[(((y * (size / lod)) + x) * 6) + 5] = ((y + 1) * (size / lod)) + (x + 1);
}
}
}
Mesh mesh = new Mesh();
mesh.vertices = vertices;
mesh.triangles = triangles;
GetComponent<MeshFilter>().mesh = mesh;
fileStream.Close();
}
void Update()
{
float distance = Vector3.Distance(Camera.main.transform.position, transform.position);
for (int a = 0; a < minLodDistances.Length - 1; a++)
{
if (distance >= minLodDistances[a] && distance <= maxLodDistances[a])
{
lod = a + 1;
if (prevLod != lod)
{
prevLod = lod;
load();
break;
}
}
}
}
}
Your answer
![](https://koobas.hobune.stream/wayback/20220613122528im_/https://answers.unity.com/themes/thub/images/avi.jpg)
Follow this Question
Related Questions
Textures on Terrain 3 Answers
Megaterrainish-type thing? 1 Answer
A node in a childnode? 1 Answer
Why does unity 3d delete my stuff when i open a new project? 1 Answer
Unity terrain very low FPS on mobile 0 Answers