public void Split(SplitType type) { if (hexes.Count < 1) { GameManager.Singleton.World.GetPlates().Remove(this); return; } if (type == SplitType.NORMAL) { Plate newPlate = new Plate(gen, UnityEngine.Random.ColorHSV()); newPlate.direction = (HexDirection)UnityEngine.Random.Range(0, HexConstants.MAX_DIR); int id = GameManager.Singleton.World.AddPlate(newPlate); Debug.Log("CREATING PLATE"); int q = 0; int r = 0; foreach (Hex h in hexes) { q += h.q; r += h.r; } q /= hexes.Count; r /= hexes.Count; FractionalHex fHexCenter = new FractionalHex(q, r, -q - r); Hex centerHex = fHexCenter.HexRound(); for (int i = hexes.Count - 1; i > -1; i--) { Hex cur = hexes[i]; if ((cur.q - centerHex.q) > 0) { int dist = cur.Distance(centerHex); if (dist < 2 && UnityEngine.Random.value < .5) { continue; } hexes.RemoveAt(i); newPlate.AddHex(cur); if (GameManager.Singleton.World.TryGetHexData(cur, out TileObject obj)) { obj.hexData.plateId = id; } } } } }
void Update() { if (paused) { return; } if (m_state == GenState.DONE) { return; } if (m_state != GenState.ITERATING) { m_state = GenState.ITERATING; } m_timer += Time.deltaTime; if (m_timer < 0.05f) { return; } m_timer = 0; if (m_iters > m_world.settings.numberOfIterations) { m_state = GenState.DONE; print("Done simulation!"); StopCoroutine(GenerateRoutine()); Smooth(); } // Update to World if (m_world.worldTemp.changeType != WorldTempChangeType.ICE_AGE) { if (Random.value > 1f - m_world.settings.iceAgeChance) { m_world.worldTemp.StartIceAge(new TemperatureEvent(-10, 3, 10, 6), 9); } } // Update to plates every 5 iterations. if (m_iters != 0 && m_iters % m_world.settings.itersForUpdate == 0) { for (int i = m_world.plates.Count - 1; i > -1; i--) { Plate p = m_world.plates[i]; p.direction = (HexDirection)Random.Range(0, HexConstants.MAX_DIR); p.TrySplit(); p.movementSpeed = 100f; } m_world.worldTemp.tempChange = Random.Range(-.3f, .3f); } // Hex loop Dictionary <Hex, HexData> tempData = new Dictionary <Hex, HexData>(); Dictionary <int, float> tempPlates = new Dictionary <int, float>(); for (int r = 0; r <= m_height; r++) // height { int r_offset = Mathf.FloorToInt(r / 2); for (int q = -r_offset; q <= m_width - r_offset; q++) // width with offset { Hex hex = new Hex(q, r, -q - r); if (!m_world.ContainsHex(hex)) { continue; } m_world.TryGetHexData(hex, out TileObject obj); HexData hData = obj.hexData; Plate hPlate = m_world.GetPlateByID(hData.plateId); if (!tempData.ContainsKey(hex)) { tempData.Add(hex, new HexData(hData)); } HexData tempHexData = tempData[hex]; tempHexData.temp += m_world.worldTemp.FinalTempChange; Hex dirHex = hex.Neighbor((int)hPlate.direction); bool dirInBounds = m_world.TryGetHexData(dirHex, out TileObject dirObj); if (!dirInBounds) { if (!tempPlates.ContainsKey(hPlate.id)) { tempPlates.Add(hPlate.id, hPlate.movementSpeed - -5f); } else { tempPlates[hPlate.id] += -5f; } continue; } dirHex = dirObj.hex; // Reassign hex incase world wrapping is on and we need to wrap. HexData dirData = dirObj.hexData; Plate dirPlate = m_world.GetPlateByID(dirData.plateId); if (!tempData.ContainsKey(dirHex)) { tempData.Add(dirHex, new HexData(dirData)); } HexData tempDirData = tempData[dirHex]; SimulatedLoopHex loopHex = new SimulatedLoopHex() { hex = hex, obj = obj, tempData = tempHexData, plate = hPlate, dirHex = dirHex, dirObj = dirObj, tempDirData = tempDirData }; m_world.windManager.SimulateWind(m_iters, loopHex); bool platesDiff = hPlate.id != dirPlate.id; bool platesCollide = Mathf.Abs(hPlate.direction - dirPlate.direction) == 3; bool heightGTE = hData.height >= dirData.height; tempHexData.age++; if (hPlate.movementSpeed > 0 && platesDiff) { const float HEIGHT_MOD = 20f; float spd = 0f; if (heightGTE) { tempHexData.height += HEIGHT_MOD; tempHexData.formingMoutain = true; tempHexData.moved = true; spd += (platesCollide) ? -1f : -.25f; } else { //tempHexData.height -= HEIGHT_MOD; tempHexData.formingMoutain = false; tempHexData.moved = false; spd += (platesCollide) ? -10f : -2.5f; } tempHexData.empty = false; if (!tempPlates.ContainsKey(hPlate.id)) { tempPlates.Add(hPlate.id, hPlate.movementSpeed - spd); } else { tempPlates[hPlate.id] += spd; } } else if (hPlate.movementSpeed <= 0) { tempHexData.empty = false; tempHexData.moved = false; } if (tempHexData.moved) { float mod = 1f; if (hData.isHotSpot) // Hot spots { mod += 20f + m_rand.NextFloat(0f, 10f); } if (hData.height < SEA_LVL - 55) { mod += 1; } if (hData.age < 5) // New created land gains more height { mod += 15; } if (hData.age < 50) // New created land gains more height { mod += 1f; } if (hData.height > HILL_LVL && hData.age > 100) { mod -= 2f; } if (hData.height > HILL_LVL + 55) { mod -= 3f; } if (dirData.height > HILL_LVL + 55 && hData.height < dirData.height - 25 && !dirData.isCoast && !dirData.isOcean) { mod += 3f; } if (hData.height < dirData.height - 35 && !dirData.isCoast && !dirData.isOcean) { mod += 2f; } tempDirData.height = hData.height + mod; tempDirData.empty = false; tempDirData.plateId = hPlate.id; } tempHexData.oldPlateId = hPlate.id; } } foreach (var pair in tempPlates) { Plate p = m_world.GetPlateByID(pair.Key); p.movementSpeed = pair.Value; } ApplyTiles(tempData); IterationEvent?.Invoke(m_iters, m_world); if (step) { paused = true; step = false; } m_iters++; }
private void Generate() { GameObject line = new GameObject(); var lr = line.AddComponent <LineRenderer>(); lr.positionCount = 5; lr.SetPosition(0, new Vector3(0, 0, -1)); lr.SetPosition(1, new Vector3(m_world.pixelW, 0, -1)); lr.SetPosition(2, new Vector3(m_world.pixelW, m_world.pixelH, -1)); lr.SetPosition(3, new Vector3(0, m_world.pixelH, -1)); lr.SetPosition(4, new Vector3(0, 0, -1)); lr.startWidth = 2; lr.endWidth = 2; for (int i = 0; i < m_world.settings.plates; i++) { int x = m_rand.NextInt(0, m_world.pixelW); int y = m_rand.NextInt(0, m_world.pixelH); Hex hex = m_layout.PixelToHex(new Point(x, y)).HexRound(); Plate p = new Plate(this, hex, UnityEngine.Random.ColorHSV()) { elevation = Random.Range(0f, 255f), movementSpeed = m_rand.NextFloat(MIN_SPD, MAX_SPD), direction = (HexDirection)Random.Range(0, HexConstants.DIRECTIONS - 1), }; m_world.AddPlate(p); } /* * ------------------------------------------------------ * Setting hexes to plates * ------------------------------------------------------ */ foreach (var pair in m_world.TileData) { int closestId = 0; int closest = int.MaxValue; for (int i = 0; i < m_world.settings.plates; i++) { int dist = pair.Key.Distance(m_world.plates[i].center); if (closest > dist) { closest = dist; closestId = i; } } for (int i = 0; i < m_world.settings.plates; i++) { int dist = pair.Key.Distance(HexUtils.WrapOffset(m_world.plates[i].center, m_world.size.x)); if (closest > dist) { closest = dist; closestId = i; } } pair.Value.hexData.plateId = m_world.GetPlates()[closestId].id; pair.Value.hexData.oldPlateId = m_world.GetPlates()[closestId].id; m_world.GetPlates()[closestId].AddHex(pair.Key); } }
public int AddPlate(Plate plate) { plates.Add(plate); plate.id = plateCounter++; return(plate.id); }