Unity程序化地形p2

MeshGenerator

public static MeshData GenerateTerrainMesh(float[,] heightMap,float 
heightMultiplier,AnimationCurve heightCurve)
...
meshData.vertices[vertexIndex] = new Vector3
(x + topLeftX,heightCurve.Evaluate(heightMap[x, y]) * heightMultiplier,  topLeftZ - y);

//MapGenerator.cs
const int mapChunkSize = 241;
[Range(0, 6)]
public int levelOfDetail;
float[,] noiseMap = Noise.GenerateNoiseMap(mapChunkSize, mapChunkSize, noiseScale,octaves,persistance,lacunarity,offsets,seed);

        Color[] colourMap = new Color[mapChunkSize * mapChunkSize];
        for(int y = 0;y < mapChunkSize; y++)
        {
            for(int x = 0;x < mapChunkSize; x++)
            {
                float currentHeight = noiseMap[x, y];
                for(int i = 0;i < regions.Length;i++)
                {
                    if(currentHeight <= regions[i].height)
                    {
                        colourMap[y * mapChunkSize + x] = regions[i].colour;
                        break;
                    }
                }
            }
        }
int Simplification = lod * 2;
int verticesPerLine = (width - 1) / Simplification + 1;
MeshData meshData = new MeshData(verticesPerLine, verticesPerLine);
for (int y = 0;y < height;y += Simplification){
    for(int x = 0;x < width;x += Simplification)
           //MeshGenerator.cs

然后是无限地形

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class EndlessTerrain : MonoBehaviour
{
    public const float maxViewDst = 450;
    public Transform viewer;

    public static Vector2 viewerPosition;
    int chunkSize;
    int chunkVisibleInViewDst;

    Dictionary<Vector2, TerrainChunk> terrainChunkDictionary
        = new Dictionary<Vector2, TerrainChunk>();
    List<TerrainChunk> ChunkVisUpdate = new List<TerrainChunk>();

    private void Start()
    {
        chunkSize = MapGenerator.mapChunkSize - 1;
        chunkVisibleInViewDst = Mathf.RoundToInt(maxViewDst / chunkSize);
    }

    private void Update()
    {
        viewerPosition = new Vector2(viewer.position.x, viewer.position.z);
        UpdateVisibleChunks();
    }
    void UpdateVisibleChunks()
    {
        for(int i = 0;i < ChunkVisUpdate.Count;i++)
        {
            ChunkVisUpdate[i].SetVisible(false);
        }
        ChunkVisUpdate.Clear();

        int currentChunkCoordX = Mathf.RoundToInt(viewerPosition.x / chunkSize);
        int currentChunkCoordY = Mathf.RoundToInt(viewerPosition.y / chunkSize);

        for(int yOffset = -chunkVisibleInViewDst;yOffset <= chunkVisibleInViewDst;yOffset++)
        {
            for(int xOffset = -chunkVisibleInViewDst;xOffset <= chunkVisibleInViewDst;xOffset++)
            {
                Vector2 viewedChunkCoord = new Vector2(currentChunkCoordX + xOffset, currentChunkCoordY + yOffset);
                if(terrainChunkDictionary.ContainsKey(viewedChunkCoord))
                {
                    terrainChunkDictionary[viewedChunkCoord].UpdateTerrainChunk();
                    if(terrainChunkDictionary[viewedChunkCoord].IsVisible())
                    {
                        ChunkVisUpdate.Add(terrainChunkDictionary[viewedChunkCoord]);
                    }
                }else
                {
                    terrainChunkDictionary.Add(viewedChunkCoord, new TerrainChunk(viewedChunkCoord,chunkSize,transform));
                }
            }
        }

    }
    public class TerrainChunk
    {
        GameObject meshObject;
        Vector2 position;
        Bounds bounds;

        public TerrainChunk(Vector2 coord,int size,Transform parent)
        {
            position = coord * size;
            bounds = new Bounds(position, Vector2.one * size);
            Vector3 positionV3 = new Vector3(position.x, 0, position.y);

            meshObject = GameObject.CreatePrimitive(PrimitiveType.Plane);
            meshObject.transform.position = positionV3;
            meshObject.transform.localScale = Vector3.one * size / 10f;
            meshObject.transform.parent = parent;
            SetVisible(false);
        }
        public void UpdateTerrainChunk()
        {
            float viewerDstFromNearestEdge = Mathf.Sqrt(bounds.SqrDistance(viewerPosition));
            bool visible = viewerDstFromNearestEdge <= maxViewDst;
            SetVisible(visible);
        }
        public void SetVisible(bool visible)
        {
            meshObject.SetActive(visible);
        }
        public bool IsVisible()
        {
            return meshObject.activeSelf;
        }
    }
}

Viewer就是个正方体 

 

第8集第10分钟以后的没看

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值