프로 시저 생성을 위해 노력하고 있는데, 분명히 프로가 아니지만이 가이드를 따라갔습니다 : click 그리고 몇 가지 결과가 있습니다. 현재로서는 2 가지 문제가 있습니다. 문제를 해결하는 기본적인 아이디어가 있지만 다른 의견을 듣고 싶습니다.유니티 3D의 절차 지형 프로그래밍
(단 하나의 답변에 이미이 질문을 게시했지만 일부 정보가 없거나 몇 마디로 설명하기가 불가능한 경우 전혀 응답이 없습니다.
내가 확대한다면 그들이 좀 사라는 그러나 텍스처가 부적당 남아 그것은 놀라운 : 덩어리 사이의 간격을 :
주요 문제는)이 정보를 찾을 수 있습니다.
두 번째로 볼 수 있듯이 빨간색으로 문제가 있습니다 (실제로 전화하는 법을 모르겠 음). 가이드의 자료를 사용하려고했지만 동일한 효과가 있습니다.
게다가 Perlin Noise (나는 다이아몬드 스퀘어 또는 심플 렉스를 사용할 수 있음)는 의사 무작위 알고리즘이므로 동일한 입력 매개 변수에 대해 동일한 값을 반환하므로 내 청크가 항상 같은?
내 코드 (나는 가이드에서 LibNoise 라이브러리를 사용하고 있습니다) :
서로 다른 지형 객체를 생성하고 있기 때문에 차이가 발생void Awake()
{
var settings = new TerrainChunkSettings(129, 129, 100, 40, FlatTexture, SteepTexture, TerrainMaterial);
var noiseProvider = new NoiseProvider();
for (var i = 0; i < 4; i++)
for (var j = 0; j < 4; j++)
new TerrainChunk(settings, noiseProvider, i, j).CreateTerrain();
}
public class TerrainChunkSettings
{
public int HeightmapResolution { get; private set; }
public int AlphamapResolution { get; private set; }
public int Length { get; private set; }
public int Height { get; private set; }
public Texture2D FlatTexture { get; private set; }
public Texture2D SteepTexture { get; private set; }
public Material TerrainMaterial { get; private set; }
public TerrainChunkSettings(int heightmapResolution, int alphamapResolution, int length, int height, Texture2D flatTexture, Texture2D steepTexture, Material terrainMaterial)
{
HeightmapResolution = heightmapResolution;
AlphamapResolution = alphamapResolution;
Length = length;
Height = height;
FlatTexture = flatTexture;
SteepTexture = steepTexture;
TerrainMaterial = terrainMaterial;
}
}
public class TerrainChunk
{
private Terrain Terrain { get; set; }
private TerrainChunkSettings Settings { get; set; }
private NoiseProvider NoiseProvider { get; set; }
public int X { get; private set; }
public int Z { get; private set; }
private TerrainData Data { get; set; }
private float[,] Heightmap { get; set; }
public TerrainChunk(TerrainChunkSettings settings, NoiseProvider noiseProvider, int x, int z)
{
X = x;
Z = z;
Settings = settings;
NoiseProvider = noiseProvider;
}
public void CreateTerrain()
{
var terrainData = new TerrainData();
terrainData.heightmapResolution = Settings.HeightmapResolution;
terrainData.alphamapResolution = Settings.AlphamapResolution;
var heightmap = GetHeightmap();
terrainData.SetHeights(0, 0, heightmap);
ApplyTextures(terrainData);
terrainData.size = new Vector3(Settings.Length, Settings.Height, Settings.Length);
var newTerrainGameObject = Terrain.CreateTerrainGameObject(terrainData);
newTerrainGameObject.transform.position = new Vector3(X * Settings.Length, 0, Z * Settings.Length);
Terrain = newTerrainGameObject.GetComponent<Terrain>();
Terrain.Flush();
}
private float[,] GetHeightmap()
{
var heightmap = new float[Settings.HeightmapResolution, Settings.HeightmapResolution];
for (var zRes = 0; zRes < Settings.HeightmapResolution; zRes++)
{
for (var xRes = 0; xRes < Settings.HeightmapResolution; xRes++)
{
var xCoordinate = X + (float)xRes/(Settings.HeightmapResolution - 1);
var zCoordinate = Z + (float)zRes/(Settings.HeightmapResolution - 1);
heightmap[zRes, xRes] = NoiseProvider.GetValue(xCoordinate, zCoordinate);
}
}
return heightmap;
}
private void ApplyTextures(TerrainData terrainData)
{
var flatSplat = new SplatPrototype();
var steepSplat = new SplatPrototype();
flatSplat.texture = Settings.FlatTexture;
steepSplat.texture = Settings.SteepTexture;
terrainData.splatPrototypes = new SplatPrototype[]
{
flatSplat,
steepSplat
};
terrainData.RefreshPrototypes();
var splatMap = new float[terrainData.alphamapResolution, terrainData.alphamapResolution, 2];
for (var zRes = 0; zRes < terrainData.alphamapHeight; zRes++)
{
for (var xRes = 0; xRes < terrainData.alphamapWidth; xRes++)
{
var normalizedX = (float)xRes/(terrainData.alphamapWidth - 1);
var normalizedZ = (float)zRes/(terrainData.alphamapHeight - 1);
var steepness = terrainData.GetSteepness(normalizedX, normalizedZ);
var steepnessNormalized = Mathf.Clamp(steepness/1.5f, 0, 1f);
splatMap[zRes, xRes, 0] = 1f - steepnessNormalized;
splatMap[zRes, xRes, 1] = steepnessNormalized;
}
}
terrainData.SetAlphamaps(0, 0, splatMap);
}
}
public interface INoiseProvider
{
float GetValue(float x, float z);
}
public class NoiseProvider : INoiseProvider
{
private Perlin PerlinNoiseGenerator;
public NoiseProvider()
{
PerlinNoiseGenerator = new Perlin();
}
public float GetValue(float x, float z)
{
return (float)(PerlinNoiseGenerator.GetValue(x, 0, z)/2f) + 0.5f;
}
}
귀하의 질문이 무엇인지 명확하게 할 수 있습니까? 귀하의 게시물에 3 가지 가능한 질문이 있습니다 (1. 간격, 2. 빨간색 표시 및 3. 펄린 노이즈 값). 일반적으로 스택 오버플로에 대한 질문에서 단 한 가지만 묻는 것이 좋습니다. 그러나 질문이 매우 밀접하게 관련된 경우 예외가 발생할 수 있습니다. 또한 물음표로 끝내면 문제가되는 것이 무엇인지 명확하게 알 수 있습니다. – PJvG
Perlin 노이즈에 대해서는 [Seed] 속성이있는 [GitHub의 LibNoise 라이브러리] (https://github.com/ricardojmendez/LibNoise.Unity/blob/master/Generator/Perlin.cs)에서 확인할 수 있습니다. . 다른 결과를 원하면'Perlin' 객체에 대해 다른 시드를 사용해야합니다. 만약 당신이 여전히 혼란 스럽다면 의사 랜덤 생성기와 씨드에 대해 좀 더 연구를 해보십시오. – PJvG
@PjvG 나는 게시물 당 약 1 질문 (포럼에 대한 공통 규칙)을 알고 있지만, 나는 그것들을 분리해야한다고 생각하지 않는다. 그래서, 내 자신을 명확히하려고 할 것입니다, 주요 질문은 간격에 관한 것입니다, 몇 가지 일반적인 (이 방법을해야합니다) 솔루션이 무엇입니까? 누군가가 똑같은 문제를 안고있는 경우를 대비해 마크에 대해 물었습니다. 나는 음영 옵션에서 뭔가 잘못했다고 확신했습니다. – user7803907