void EvolveClimate(int cellIndex) { TriCell cell = grid.GetCell(cellIndex); ClimateData cellClimate = climate[cellIndex]; float tMoisture = cellClimate.moisture, tClouds = cellClimate.clouds; if (cell.IsUnderwater) { tMoisture = 1f; tClouds += evaporationFactor; } else { float evaporation = tMoisture * evaporationFactor; tMoisture -= evaporation; tClouds += evaporation; } float precipitation = tClouds * precipitationFactor; tClouds -= precipitation; tMoisture += precipitation; //SetClimateData(cellIndex, tMoisture, tClouds); float cloudDispersal = tClouds * (1f / 6f); float runoff = tMoisture * runoffFactor * (1f / 6f); for (int i = 0; i < 4; i++) { TriCell neighbor = grid.GetCell(TriMetrics.TriToHex(cell.coordinates) + new Vector2Int(TriMetrics.hexDir[i, 0], TriMetrics.hexDir[i, 1])); if (!neighbor) { continue; } ClimateData neighborClimate = climate[neighbor.Index]; float tNMoisture = neighborClimate.moisture, tNClouds = neighborClimate.clouds; tNClouds += cloudDispersal; int elevationDelta = neighbor.Elevation - cell.Elevation; if (elevationDelta < 0) { tMoisture -= runoff; tNMoisture += runoff; } SetClimateData(neighbor.Index, tNMoisture, tNClouds); //climate[neighbor.Index] = neighborClimate; } tClouds = 0f; SetClimateData(cellIndex, tMoisture, tClouds); //climate[cellIndex] = cellClimate; }
void CreateClimate() { climate.Clear(); ClimateData initialData = new ClimateData(); for (int i = 0; i < cellCount; i++) { climate.Add(initialData); } for (int cycle = 0; cycle < 40; cycle++) { for (int i = 0; i < cellCount; i++) { TriCoordinates t = grid.GetCell(i).coordinates; if (t == TriMetrics.TriToHex(t)) { EvolveClimate(i); } } } }
IEnumerator <WaitForEndOfFrame> CreateClimate() { climate.Clear(); ClimateData initialData = new ClimateData(); for (int i = 0; i < cellCount; i++) { climate.Add(initialData); } for (int cycle = 0; cycle < 40; cycle++) { for (int i = 0; i < cellCount; i++) { TriCoordinates t = grid.GetCell(i).coordinates; if (t == TriMetrics.TriToHex(t)) { EvolveClimate(i); } } } yield return(null); }
TriCell GetRandomCell() { TriCoordinates t = TriMetrics.TriToHex(new TriCoordinates(Random.Range(xMin, xMax), Random.Range(zMin, zMax))); return(grid.GetCell(t.X, t.Z)); }
IEnumerator <WaitForEndOfFrame> SetTerrainType() { for (int i = 0; i < cellCount; i++) { TriCell cell = grid.GetCell(i), hexCell = grid.GetCell(TriMetrics.TriToHex(cell.coordinates)); if (cell.coordinates == hexCell.coordinates) { float moisture = climate[hexCell.Index].moisture; TriDirection d = TriDirection.VERT; TriIsland isle = TriIsland.Instance; for (int j = 0; j < 6; j++) { if (!cell) { break; } if (!cell.IsUnderwater) { if (cell.Elevation > 10) { cell.TerrainTypeIndex = 4; } else if (moisture < 0.02f) { cell.TerrainTypeIndex = 3; if (Random.value < 0.5f && !cell.HasRiver) { Tree t = (Tree)Instantiate(TriIsland.GetNaturalPrefabs((int)NaturalType.TREE, 0), isle.transform); t.Location = cell; t.EntranceDirection = (TriDirection)((int)(Random.value * 3f)); entities.AddNatural(t); } } else if (moisture < 0.12f) { cell.TerrainTypeIndex = 2; if (Random.value < 0.2f && !cell.HasRiver) { Tree t = (Tree)Instantiate(TriIsland.GetNaturalPrefabs((int)NaturalType.TREE, 0), isle.transform); t.Location = cell; t.EntranceDirection = (TriDirection)((int)(Random.value * 3f)); entities.AddNatural(t); } } else if (moisture < 0.20f) { cell.TerrainTypeIndex = 1; } else if (moisture < 0.85f) { cell.TerrainTypeIndex = 0; } else { cell.TerrainTypeIndex = 0; } } else { cell.TerrainTypeIndex = 1; } cell = cell.GetNeighbor(d); if (hexCell.inverted) { d = d.Next(); } else { d = d.Previous(); } } if (i % Metrics.refreshLimit == 0) { yield return(null); } } } }
int RaiseTerrain(int chunkSize, int budget, bool initiated) { searchFrontierPhase += 1; TriCoordinates center = grid.GetCell(grid.cellCountX / 2, grid.cellCountZ / 2).coordinates; center = TriMetrics.TriToHex(center); TriCell firstCell = grid.GetCell(center.X, center.Z); if (initiated) { do { firstCell = GetRandomCell(); } while (firstCell.Elevation < 1); } searchFrontier.Enqueue(firstCell); center = firstCell.coordinates; checker.Add(center); int size = 0; while (size < chunkSize && searchFrontier.Count > 0) { TriCell current = searchFrontier.Dequeue(); if (current.Elevation < elevationMaximum) { TriDirection d = TriDirection.VERT; TriCell k = current; if (k.Elevation < elevationMaximum) { if (k.Elevation == 0) { budget -= 6; } for (int i = 0; i < 6; i++) { if (!k) { break; } k.Elevation += 1; k = k.GetNeighbor(d); if (current.inverted) { d = d.Next(); } else { d = d.Previous(); } } } } if (current.Elevation == 1 && budget == 0) { break; } size += 6; TriCoordinates coord = current.coordinates; for (int i = 0; i < 4; i++) { TriCell neighbor = grid.GetCell(coord.X + TriMetrics.hexDir[i, 0], coord.Z + TriMetrics.hexDir[i, 1]); if (neighbor && checkbounds(neighbor.coordinates) && !checker.Contains(neighbor.coordinates) && (i == 3 || Random.value < jitterProbability ? true : false)) { searchFrontier.Enqueue(neighbor); checker.Add(neighbor.coordinates); } } } searchFrontier.Clear(); checker.Clear(); return(budget); }