コード例 #1
0
                public static void Conify(TerraMesh _tMesh, float _strength, Progress.OnUpdate _onUpdate = null)
                {
                    if (_onUpdate == null)
                    {
                        _onUpdate = (_prog, _str) => { }
                    }
                    ;
                    var prog = new Progress();

                    prog.SetOnUpdate(_onUpdate);

                    var cent   = _tMesh.m_Bounds.center.ToVec2();
                    var min    = _tMesh.m_Bounds.min.ToVec2();
                    var maxMag = (min - cent).magnitude;

                    prog.Update(0, "Conifying");
                    for (var sIdx = 0; sIdx < _tMesh.Vertices.Length; ++sIdx)
                    {
                        var sitePos = _tMesh.Vertices[sIdx];
                        var magScal = (new Vector2(sitePos.x, sitePos.y) - cent).magnitude / maxMag - 0.5f;
                        var zShift  = magScal * _strength / 2f;
                        var newPos  = new Vector3(sitePos.x, sitePos.y, zShift + sitePos.z);
                        _tMesh.Vertices[sIdx] = newPos;
                        prog.Update((float)sIdx / _tMesh.Vertices.Length);
                    }
                    _tMesh.RecalculateBounds();
                }
コード例 #2
0
ファイル: TestTerraMesh.cs プロジェクト: phildo77/ioTerraMap
        public void TestGenerate()
        {
            var sets      = TerraMap.Settings.Default;
            var width     = sets.Bounds.width;
            var height    = sets.Bounds.height;
            var density   = sets.Resolution;
            var seed      = sets.Seed;
            var vertices  = TerraMap.TerraMesh.Generator.GenerateRandomVertices(width, height, density, seed);
            var generator = TerraMap.TerraMesh.Generator.StageMeshGeneration(vertices);

            TerraMap.TerraMesh tMesh;

            Progress.OnUpdate onUpdate = (_pct, _str) => Trace.WriteLine(_str + " : " + _pct);
            TerraMap.TerraMesh.Generator.OnComplete onComplete = _tm => tMesh = _tm;

            var genThread = new Thread(() => generator.Generate(onUpdate, onComplete));

            genThread.Start();

            var secondCounter = 0;

            while (genThread.IsAlive)
            {
                Trace.WriteLine("Waiting for thread: " + secondCounter++);
                System.Threading.Thread.Sleep(1000);
            }
        }
コード例 #3
0
            private void GenerateTMesh(Progress.OnUpdate _onUpdate = null)
            {
                var onUpdate = _onUpdate ?? ((_progPct, _progStr) => { });

                m_Prog.SetOnUpdate(onUpdate);

                void TMeshOnComplete(TerraMesh _tMesh)
                {
                    m_TerraMap.TMesh = _tMesh;
                }

                var settings     = m_TerraMap.settings;
                var width        = settings.Bounds.height;
                var height       = settings.Bounds.height;
                var pointDensity = settings.Resolution;
                var seed         = settings.Seed;

                if (Vertices == null)
                {
                    Vertices = TerraMesh.Generator.GenerateRandomVertices(width, height, pointDensity, seed);
                }
                var terraMeshGen = TerraMesh.Generator.StageMeshGeneration(Vertices);

                terraMeshGen.Generate(_onUpdate, TMeshOnComplete);

                //TerraMesh.Generator.Generate(_gen.m_TerraMap.settings, onUpdate, TMeshOnComplete);
            }
コード例 #4
0
            public void Generate(OnComplete _onComplete, Progress.OnUpdate _onUpdate)
            {
                GenerateTMesh(_onUpdate);

                //Temp TODO
                m_Prog.Update(0, "Creating Map Texture", true);
                m_TerraMap.TTex = new TerraTexture(m_TerraMap, _onUpdate);
                m_Prog.Update(1, "Creating Map Texture", true);
                m_Prog.Update(0, "Creating Biomes", true);
                m_TerraMap.TBiome = new BiomeStuff(m_TerraMap);
                m_Prog.Update(1, "Creating Biomes", true);
                _onComplete(m_TerraMap);
            }
コード例 #5
0
        public void TestSerializationTerraMesh()
        {
            var fullFileName = FilePath + "\\TerraMesh" + FileName;

            var resolution = 1f;
            var sets       = new TerraMap.Settings();

            sets.Resolution     = 1;
            sets.Bounds         = new Rect(Vector2.one, 256 * Vector2.one);
            sets.GlobalSlopeDir = Vector2.left;

            Progress.OnUpdate progOnUpdate = (_pct, _str) =>
            {
                Trace.WriteLine(_str);
                Trace.WriteLine(_pct * 100 + "%");
            };


            var      isDone      = false;
            TerraMap finishedMap = null;

            TerraMap.Generator.OnComplete onComplete = _tMap =>
            {
                finishedMap = _tMap;
                isDone      = true;
            };
            var gen       = TerraMap.Generator.StageMapCreation(sets);
            var genThread = new Thread(() => gen.Generate(onComplete, progOnUpdate));

            genThread.Start();

            while (isDone == false)
            {
                Thread.Sleep(100);
            }

            var mapExists = finishedMap != null;

            var tMeshOrig       = finishedMap.TMesh;
            var serializedTMesh = TerraMap.TerraMesh.Serialize(tMeshOrig);

            File.WriteAllBytes(fullFileName, serializedTMesh);

            var dataFromFile = File.ReadAllBytes(fullFileName);

            var tMeshFromFile = TerraMap.TerraMesh.Deserialize(dataFromFile);

            Assert.True(true);
        }
コード例 #6
0
            public TerraTexture(TerraMap _host, Progress.OnUpdate _onUpdate = null)
            {
                Host   = _host;
                canvas = new Canvas((int)Math.Ceiling(Host.settings.TextureResolution * Host.settings.Bounds.width),
                                    (int)Math.Ceiling(Host.settings.TextureResolution * Host.settings.Bounds.height));

                m_Progress = new Progress("TerraTexture");
                var actProg = _onUpdate ?? ((_progPct, _progStr) => { });

                m_Progress.SetOnUpdate(actProg);
                m_PixSize    = new Vector2(Host.TMesh.bounds.size.x / canvas.Width, Host.TMesh.bounds.size.y / canvas.Height);
                m_ZeroOffset = Host.TMesh.bounds.min.ToVec2();

                Trace.WriteLine("Init Texture W: " + canvas.Width + " H: " + canvas.Height);

                //Paint Waterways

                //PaintRivers();
            }
コード例 #7
0
ファイル: Tests.cs プロジェクト: phildo77/ioTerraMap
        public void Test1()
        {
            var resolution = 1f;
            var sets       = new TerraMap.Settings();

            sets.Resolution     = 1;
            sets.Bounds         = new Rect(Vector2.one, 256 * Vector2.one);
            sets.GlobalSlopeDir = Vector2.left;

            Progress.OnUpdate progOnUpdate = (_pct, _str) =>
            {
                Trace.WriteLine(_str);
                Trace.WriteLine(_pct * 100 + "%");
            };


            var      isDone      = false;
            TerraMap finishedMap = null;

            TerraMap.Generator.OnComplete onComplete = _tMap =>
            {
                finishedMap = _tMap;
                isDone      = true;
            };
            var gen       = TerraMap.Generator.StageMapCreation(sets);
            var genThread = new Thread(() => gen.Generate(onComplete, progOnUpdate));

            genThread.Start();

            while (isDone == false)
            {
                Thread.Sleep(100);
            }

            var mapExists = finishedMap != null;


            Assert.True(mapExists);
        }
コード例 #8
0
                public void Generate(Progress.OnUpdate _onUpdate, OnComplete _onComplete)
                {
                    ProgOnUpdate = _onUpdate;
                    ProgressGenerator.SetOnUpdate(_onUpdate);

                    //Create and triangluate Delaunay
                    DoDelaunayTriangulation();

                    //Create Voronoi and Lloyd Relax
                    DoVoronoiAndRelax();

                    //Build TerraMesh Object
                    var mesh = Delaunay.Mesh;

                    TMesh = new TerraMesh(mesh.Vertices, mesh.Triangles);

                    IndexSites();
                    ComputeSiteData();
                    PopulateHullSites();

                    _onComplete(TMesh);
                }
コード例 #9
0
                public static void SlopeGlobal(TerraMesh _tMesh, Vector2 _dir, float _strength,
                                               Progress.OnUpdate _onUpdate = null)
                {
                    if (_onUpdate == null)
                    {
                        _onUpdate = (_prog, _str) => { }
                    }
                    ;
                    var prog = new Progress();

                    prog.SetOnUpdate(_onUpdate);


                    var dir  = _dir.normalized;
                    var bnds = _tMesh.bounds;
                    Func <Vector3, float> strf = _pos =>
                    {
                        var xPct = (_pos.x - bnds.min.x) / bnds.size.x - 0.5f;
                        var yPct = (_pos.y - bnds.min.y) / bnds.size.y - 0.5f;
                        var xStr = xPct * dir.x;
                        var yStr = yPct * dir.y;
                        return((xStr + yStr) * _strength / 4f);
                    };

                    prog.Update(0, "Global Slope");
                    for (var sIdx = 0; sIdx < _tMesh.Vertices.Length; ++sIdx)
                    {
                        //if (_tMesh.HullSites.Contains(sIdx))
                        //    Trace.WriteLine("Debug Hullsites"); //TODO DEbug
                        var sitePos = _tMesh.Vertices[sIdx];
                        var zShift  = strf(sitePos);
                        var newZ    = sitePos.z + zShift;
                        var newPos  = new Vector3(sitePos.x, sitePos.y, newZ);
                        _tMesh.Vertices[sIdx] = newPos;
                        prog.Update((float)sIdx / _tMesh.Vertices.Length);
                    }
                    _tMesh.RecalculateBounds();
                }
コード例 #10
0
                public static Vector3[] PlanchonDarboux(TerraMesh _tMesh, float _minSlope, Progress.OnUpdate _onUpdate)
                {
                    var prog = new Progress("PlanchonDarboux");

                    prog.SetOnUpdate(_onUpdate);
                    var sitePosArr = _tMesh.GetAllSitePositions(); //TODO slow?
                    var hullSites  = new HashSet <int>(_tMesh.HullSites);
                    //var hullSites = _tMesh.HullSites;

                    //Generate waterflow surface points
                    var newSurf = new Vector3[sitePosArr.Length];

                    for (var pIdx = 0; pIdx < sitePosArr.Length; ++pIdx)
                    {
                        var sPos = sitePosArr[pIdx];
                        var z    = float.PositiveInfinity;
                        if (hullSites.Contains(pIdx))
                        {
                            z = sPos.z;
                        }
                        newSurf[pIdx] = new Vector3(sPos.x, sPos.y, z);
                    }

                    Func <int, float>      Z = _idx => sitePosArr[_idx].z;
                    Func <int, float>      W = _idx => newSurf[_idx].z;
                    Func <int, int, float> E = (_cIdx, _nIdx) =>
                    {
                        var cVert = sitePosArr[_cIdx];
                        var nVert = sitePosArr[_nIdx];
                        var subX  = nVert.x - cVert.x;
                        var subY  = nVert.y - cVert.y;
                        return((float)Math.Sqrt(subX * subX + subY * subY) * _minSlope);
                    };


                    var opDone = false;
                    var wCnt   = 0; //DEBUG todo

                    do
                    {
                        opDone = false;
                        var sitePosArrLen = sitePosArr.Length; //TODO Debug
                        for (var pIdx = 0; pIdx < sitePosArrLen; ++pIdx)
                        {
                            var progPct = (float)pIdx / sitePosArrLen;
                            prog.Update(progPct, pIdx + " of " + sitePosArrLen);
                            if (hullSites.Contains(pIdx))
                            {
                                continue;
                            }
                            var sitePos = sitePosArr[pIdx];
                            var c       = pIdx;
                            if (!(W(c) > Z(c)))
                            {
                                continue;
                            }
                            var cVertZ = sitePos;
                            foreach (var n in _tMesh.SiteNeighbors[pIdx])
                            {
                                var e   = E(c, n);
                                var wpn = W(n) + e;
                                if (cVertZ.z >= wpn)
                                {
                                    newSurf[c].Set(cVertZ.x, cVertZ.y, cVertZ.z);
                                    opDone = true;
                                    break;
                                }

                                if (W(c) > wpn)
                                {
                                    newSurf[c].Set(cVertZ.x, cVertZ.y, wpn);
                                    opDone = true;
                                }
                            }
                        }

                        if (++wCnt > 2)
                        {
                            break;             // TODO DEBUG
                        }
                    } while (opDone);

                    return(newSurf);
                }
コード例 #11
0
            //TODO split old settings add new settings for just this.
            public static void ApplyRandomLandFeatures(TerraMap _tMap, Action _onComplete, Progress.OnUpdate _onUpdate)
            {
                var prog = new Progress();

                prog.SetOnUpdate(_onUpdate);
                var tMesh    = _tMap.TMesh;
                var settings = _tMap.settings;

                //Land morphing

                prog.Update(0, "Conifying", true);
                TerraMesh.Modify.Conify(tMesh, settings.ConifyStrength, _onUpdate);
                prog.Update(1, "Conifying", true);

                prog.Update(0, "Applying Global Slope", true);
                var gSlpDir = settings.GlobalSlopeDir == Vector2.zero
                    ? new Vector2((float)(settings.m_Rnd.NextDouble() - 0.5f),
                                  (float)(settings.m_Rnd.NextDouble() - 0.5f))
                    : settings.GlobalSlopeDir;

                TerraMesh.Modify.SlopeGlobal(tMesh, gSlpDir, settings.GlobalSlopeMag);
                prog.Update(1, "Applying Global Slope", true);

                prog.Update(0, "Adding Hills / Blobs", true);
                var meshBnd = tMesh.bounds;
                var rectXY  = new Rect(meshBnd.min.x, meshBnd.min.y, meshBnd.size.x, meshBnd.size.y);

                for (var hIdx = 0; hIdx < settings.HillRndCnt.Count; ++hIdx)
                {
                    prog.Update((float)hIdx / settings.HillRndCnt.Count, "Adding hills / blobs");
                    for (var hCnt = 0; hCnt < settings.HillRndCnt[hIdx]; ++hCnt)
                    {
                        TerraMesh.Modify.Blob(tMesh, settings.HillRndStr[hIdx], settings.HillRndRad[hIdx],
                                              Settings.RndVec2(rectXY, settings.m_Rnd));
                    }
                }

                prog.Update(1, "Adding Hills / Blobs", true);


                //Calculate water flux
                prog.Update(0, "Making Rivers", true);
                ApplyWaterFlux(_tMap, _onUpdate);
                prog.Update(1, "Making Rivers", true);

                //Erosion
                prog.Update(0, "Eroding", true);
                TerraMesh.Modify.Erode(tMesh, settings.MaxErosionRate,
                                       _tMap.WaterFlux.Select(_node => _node.Flux).ToArray());
                prog.Update(1, "Eroding", true);

                //Calculate Water Level
                prog.Update(0, "Setting Sea Level", true);
                SetSeaLevelByLandRatio(_tMap, settings.LandWaterRatio);
                prog.Update(1, "Setting Sea Level", true);



                PlaceRivers(_tMap, settings.m_WaterwayThresh);
            }
コード例 #12
0
            //TODO - consider wind effect on rain?  ie less rain on downward slopes?
            public static void ApplyWaterFlux(TerraMap _tMap, Progress.OnUpdate _onUpdate)
            {
                var pdSurface = TerraMesh.Generator.PlanchonDarboux(_tMap.TMesh, _tMap.settings.MinPDSlope, _onUpdate);

                //Calc water flux
                var sitePos = _tMap.TMesh.GetAllSitePositions();

                _tMap.WaterFlux = new WaterNode[sitePos.Length];

                //Init waterflux and heightmap - TODO sort not needed?
                var pIdxByHt = new int[sitePos.Length];

                for (var pIdx = 0; pIdx < sitePos.Length; ++pIdx)
                {
                    pIdxByHt[pIdx]        = pIdx;
                    _tMap.WaterFlux[pIdx] = new WaterNode
                    {
                        Flux    = _tMap.settings.RainfallGlobal,
                        SiteIdx = pIdx
                    };
                }

                Array.Sort(pIdxByHt, (_a, _b) => pdSurface[_b].z.CompareTo(pdSurface[_a].z));

                var dbgHtArr = new float[pIdxByHt.Length];

                for (var idx = 0; idx < pIdxByHt.Length; idx++)
                {
                    dbgHtArr[idx] = pdSurface[pIdxByHt[idx]].z;
                }


                for (var hIdx = 0; hIdx < sitePos.Length; ++hIdx)
                {
                    var pIdx = pIdxByHt[hIdx];
                    var w    = pdSurface[pIdx];

                    //Find biggest slope neighbor
                    var minNIdx = -1;
                    //var maxNSlp = 0f;
                    float maxZdiff = 0;
                    var   siteNbrs = _tMap.TMesh.SiteNeighbors;
                    foreach (var nIdx in siteNbrs[pIdx])
                    {
                        if (nIdx == TerraMesh.SiteIdxNull)
                        {
                            continue;
                        }
                        var n = pdSurface[nIdx];

                        if (n.z <= w.z)
                        {
                            var diff = w.z - n.z;
                            if (diff > maxZdiff)
                            {
                                maxZdiff = diff;
                                minNIdx  = nIdx;
                            }

                            /*  Use slope - (Not working?)
                             * var vec = n - w;
                             * var run = (float) Math.Sqrt(vec.x * vec.x + vec.y * vec.y);
                             * var rise = w.z - n.z;
                             * var slp = rise / run;
                             * if (slp > maxNSlp)
                             * {
                             *  minNIdx = nIdx;
                             *  maxNSlp = slp;
                             * }
                             */
                        }
                    }

                    if (minNIdx == -1) //TODO DEBUG should never happen?
                    {
                        continue;
                    }
                    if (minNIdx == pIdx) //TODO DEBUG
                    {
                        continue;
                    }

                    //Add this nodes flux to downhill neighbor
                    _tMap.WaterFlux[minNIdx].Flux += _tMap.WaterFlux[pIdx].Flux;
                    //Set waterway direction
                    _tMap.WaterFlux[pIdx].NodeTo = _tMap.WaterFlux[minNIdx];

                    //Check min / max
                    var chkFlx = _tMap.WaterFlux[minNIdx].Flux;
                    if (chkFlx > _tMap.WaterFluxMax)
                    {
                        _tMap.WaterFluxMax = chkFlx;
                    }
                }
            }