public void Process(GTerrainChunk chunk, ref GPolygon p)
        {
            Texture2D albedo = chunk.Terrain.TerrainData.Shading.AlbedoMap;
            Color     c0     = albedo.GetPixelBilinear(p.Uvs[0].x, p.Uvs[0].y);
            Color     c1     = albedo.GetPixelBilinear(p.Uvs[1].x, p.Uvs[1].y);
            Color     c2     = albedo.GetPixelBilinear(p.Uvs[2].x, p.Uvs[2].y);

            p.VertexColors = new List <Color32>(3);
            p.VertexColors.Add(c0);
            p.VertexColors.Add(c1);
            p.VertexColors.Add(c2);
        }
Example #2
0
        public void Process(GTerrainChunk chunk, ref GPolygon p)
        {
            Texture2D albedo = chunk.Terrain.TerrainData.Shading.AlbedoMap;
            Vector2   uv     = (p.Uvs[0] + p.Uvs[1] + p.Uvs[2]) / 3;

            Color c = albedo.GetPixelBilinear(uv.x, uv.y);

            p.VertexColors = new List <Color32>(3);
            p.VertexColors.Add(c);
            p.VertexColors.Add(c);
            p.VertexColors.Add(c);
        }
        public void Process(GTerrainChunk chunk, ref GPolygon p)
        {
            Vector2 uv0  = p.Uvs[0];
            Vector2 uv1  = p.Uvs[1];
            Vector2 uv2  = p.Uvs[2];
            Vector2 uv01 = (uv0 + uv1) * 0.5f;
            Vector2 uv12 = (uv1 + uv2) * 0.5f;
            Vector2 uv20 = (uv2 + uv0) * 0.5f;

            Vector3 v0  = p.Vertices[0];
            Vector3 v1  = p.Vertices[1];
            Vector3 v2  = p.Vertices[2];
            Vector3 v01 = (v0 + v1) * 0.5f;
            Vector3 v12 = (v1 + v2) * 0.5f;
            Vector3 v20 = (v2 + v0) * 0.5f;

            v01.y = chunk.Terrain.GetInterpolatedHeightMapSample(uv01).x *chunk.Terrain.TerrainData.Geometry.Height;
            v12.y = chunk.Terrain.GetInterpolatedHeightMapSample(uv12).x *chunk.Terrain.TerrainData.Geometry.Height;
            v20.y = chunk.Terrain.GetInterpolatedHeightMapSample(uv20).x *chunk.Terrain.TerrainData.Geometry.Height;

            p.Vertices.Clear();
            p.Vertices.Add(v0); p.Vertices.Add(v01); p.Vertices.Add(v20);
            p.Vertices.Add(v1); p.Vertices.Add(v12); p.Vertices.Add(v01);
            p.Vertices.Add(v2); p.Vertices.Add(v20); p.Vertices.Add(v12);
            p.Vertices.Add(v01); p.Vertices.Add(v12); p.Vertices.Add(v20);

            p.Uvs.Clear();
            p.Uvs.Add(uv0); p.Uvs.Add(uv01); p.Uvs.Add(uv20);
            p.Uvs.Add(uv1); p.Uvs.Add(uv12); p.Uvs.Add(uv01);
            p.Uvs.Add(uv2); p.Uvs.Add(uv20); p.Uvs.Add(uv12);
            p.Uvs.Add(uv01); p.Uvs.Add(uv12); p.Uvs.Add(uv20);

            p.Triangles.Clear();
            p.Triangles.Add(0); p.Triangles.Add(1); p.Triangles.Add(2);
            p.Triangles.Add(3); p.Triangles.Add(4); p.Triangles.Add(5);
            p.Triangles.Add(6); p.Triangles.Add(7); p.Triangles.Add(8);
            p.Triangles.Add(9); p.Triangles.Add(10); p.Triangles.Add(11);
        }
Example #4
0
        private void CreatePolygons(GSubDivisionTree tree)
        {
            int       dispSeed = Terrain.TerrainData.Geometry.DisplacementSeed;
            float     dispStrength = Terrain.TerrainData.Geometry.DisplacementStrength;
            Texture2D subdivMap = Terrain.TerrainData.Geometry.Internal_SubDivisionMap;
            Vector2   uv0, uv1, uv2;
            Vector3   v0, v1, v2;
            float     r;
            Rand      rand;
            double    radius;

            int    baseResolution = Terrain.TerrainData.Geometry.MeshBaseResolution;
            int    resolution     = Terrain.TerrainData.Geometry.MeshResolution;
            int    level;
            double triangleBaseLength = 1f / Terrain.TerrainData.Geometry.ChunkGridSize;

            IGPolygonProcessor pp      = Terrain.TerrainData.Geometry.PolygonProcessor;
            GPolygon           polygon = new GPolygon();

            GeneratedUv.Clear();
            GeneratedVertices.Clear();
            GeneratedVertexColors.Clear();
            GeneratedTriangles.Clear();

            Vector3 terrainSize = new Vector3(
                Terrain.TerrainData.Geometry.Width,
                Terrain.TerrainData.Geometry.Height,
                Terrain.TerrainData.Geometry.Length);

            v0 = Vector3.zero;
            v1 = Vector3.zero;
            v2 = Vector3.zero;

            tree.ForEachLeaf((n) =>
            {
                uv0 = n.V0;
                uv1 = n.V1;
                uv2 = n.V2;
                if (dispStrength > 0)
                {
                    if (uv0.x != 0 && uv0.x != 1 && uv0.y != 0 && uv0.y != 1)
                    {
                        r      = subdivMap.GetPixelBilinear(uv0.x, uv0.y).r;
                        level  = baseResolution + Mathf.Min(Mathf.FloorToInt(r / GCommon.SUB_DIV_STEP), resolution - baseResolution);
                        rand   = new Rand(dispSeed + (int)(uv0.x * 1000 + uv0.y * 1000));
                        radius = 0.35 * dispStrength * triangleBaseLength * TriangleEdgeLength[level];
                        uv0.x  = Mathf.Clamp01(uv0.x + (float)((rand.NextDouble() - 0.5) * radius));
                        uv0.y  = Mathf.Clamp01(uv0.y + (float)((rand.NextDouble() - 0.5) * radius));
                    }

                    if (uv1.x != 0 && uv1.x != 1 && uv1.y != 0 && uv1.y != 1)
                    {
                        r      = subdivMap.GetPixelBilinear(uv1.x, uv1.y).r;
                        level  = baseResolution + Mathf.Min(Mathf.FloorToInt(r / GCommon.SUB_DIV_STEP), resolution - baseResolution);
                        rand   = new Rand(dispSeed + (int)(uv1.x * 1000 + uv1.y * 1000));
                        radius = 0.35 * dispStrength * triangleBaseLength * TriangleEdgeLength[level];
                        uv1.x  = Mathf.Clamp01(uv1.x + (float)((rand.NextDouble() - 0.5) * radius));
                        uv1.y  = Mathf.Clamp01(uv1.y + (float)((rand.NextDouble() - 0.5) * radius));
                    }

                    if (uv2.x != 0 && uv2.x != 1 && uv2.y != 0 && uv2.y != 1)
                    {
                        r      = subdivMap.GetPixelBilinear(uv2.x, uv2.y).r;
                        level  = baseResolution + Mathf.Min(Mathf.FloorToInt(r / GCommon.SUB_DIV_STEP), resolution - baseResolution);
                        rand   = new Rand(dispSeed + (int)(uv2.x * 1000 + uv2.y * 1000));
                        radius = 0.35 * dispStrength * triangleBaseLength * TriangleEdgeLength[level];
                        uv2.x  = Mathf.Clamp01(uv2.x + (float)((rand.NextDouble() - 0.5) * radius));
                        uv2.y  = Mathf.Clamp01(uv2.y + (float)((rand.NextDouble() - 0.5) * radius));
                    }
                }

                Vector4 h0 = Terrain.GetInterpolatedHeightMapSample(uv0);
                Vector4 h1 = Terrain.GetInterpolatedHeightMapSample(uv1);
                Vector4 h2 = Terrain.GetInterpolatedHeightMapSample(uv2);
                if (h0.w >= 0.5f || h1.w >= 0.5f || h2.w >= 0.5f) //alpha channel for visibility
                {
                    return;
                }

                if (pp != null)
                {
                    polygon.Clear();
                    v0.Set(uv0.x * terrainSize.x, h0.x * terrainSize.y, uv0.y * terrainSize.z);
                    v1.Set(uv1.x * terrainSize.x, h1.x * terrainSize.y, uv1.y * terrainSize.z);
                    v2.Set(uv2.x * terrainSize.x, h2.x * terrainSize.y, uv2.y * terrainSize.z);
                    polygon.Vertices.Add(v0);
                    polygon.Vertices.Add(v1);
                    polygon.Vertices.Add(v2);
                    polygon.Uvs.Add(uv0);
                    polygon.Uvs.Add(uv1);
                    polygon.Uvs.Add(uv2);
                    polygon.Triangles.Add(0);
                    polygon.Triangles.Add(1);
                    polygon.Triangles.Add(2);
                    pp.Process(this, ref polygon);

                    int currentTrisIndex = GeneratedVertices.Count;
                    for (int i = 0; i < polygon.Triangles.Count; ++i)
                    {
                        GeneratedTriangles.Add(currentTrisIndex + polygon.Triangles[i]);
                    }

                    for (int i = 0; i < polygon.Vertices.Count; ++i)
                    {
                        GeneratedVertices.Add(polygon.Vertices[i]);
                    }

                    for (int i = 0; i < polygon.Uvs.Count; ++i)
                    {
                        GeneratedUv.Add(polygon.Uvs[i]);
                    }

                    if (polygon.VertexColors != null && polygon.VertexColors.Count > 0)
                    {
                        for (int i = 0; i < polygon.VertexColors.Count; ++i)
                        {
                            GeneratedVertexColors.Add(polygon.VertexColors[i]);
                        }
                    }
                }
                else
                {
                    int currentTrisIndex = GeneratedVertices.Count;
                    GeneratedTriangles.Add(currentTrisIndex + 0);
                    GeneratedTriangles.Add(currentTrisIndex + 1);
                    GeneratedTriangles.Add(currentTrisIndex + 2);
                    v0.Set(uv0.x * terrainSize.x, h0.x * terrainSize.y, uv0.y * terrainSize.z);
                    v1.Set(uv1.x * terrainSize.x, h1.x * terrainSize.y, uv1.y * terrainSize.z);
                    v2.Set(uv2.x * terrainSize.x, h2.x * terrainSize.y, uv2.y * terrainSize.z);
                    GeneratedVertices.Add(v0);
                    GeneratedVertices.Add(v1);
                    GeneratedVertices.Add(v2);
                    GeneratedUv.Add(uv0);
                    GeneratedUv.Add(uv1);
                    GeneratedUv.Add(uv2);
                }
            });

            //Convert vertices terrain local space to chunk local space.
            //This way we can place the chunk pivot/origin point at the center of its region instead of the terrain pivot.
            //Chunk position is set by the terrain component.
            //This step is very important for other task such as level streaming and occlusion culling, etc.
            //Special thank to Aleš Stupka for the contribution.
            Matrix4x4 vertexTransformMatrix = Terrain.transform.localToWorldMatrix * transform.worldToLocalMatrix;

            for (int i = 0; i < GeneratedVertices.Count; ++i)
            {
                GeneratedVertices[i] = vertexTransformMatrix.MultiplyPoint(GeneratedVertices[i]);
            }
        }