void Update() { if (Input.GetKeyDown(KeyCode.Escape)) { EnableEscMenu(!Paused); } else if (!Paused) { // place something if (grabbed != null) { Ray ray = camera.ScreenPointToRay(Input.mousePosition); RaycastHit hit; if (Physics.Raycast(ray, out hit, 100f, LayerMask.GetMask("Terrain"))) { Vector3 placePosition = hit.point; grabbed.transform.position = placePosition; if (Input.GetMouseButtonDown(0)) { HexTile tile = GetTileAtMousePosition(); if (tile != null) { ///TODO Clean this up Goat goat = grabbed.GetComponent <Goat>(); if (goat != null) { goats.Add(goat); UpdatePotentialEnergy(); } Cow cow = grabbed.GetComponent <Cow>(); if (cow != null) { cows.Add(cow); UpdatePotentialEnergy(); } Wolf wolf = grabbed.GetComponent <Wolf>(); if (wolf != null) { wolves.Add(wolf); UpdatePotentialEnergy(); } grabbed.Grabbed = false; grabbed = null; } } } else { if (Input.GetMouseButtonDown(0)) { // operation was cancelled Destroy(grabbed.gameObject); grabbed = null; } } } else if (IsExpansionMode) { Ray ray = camera.ScreenPointToRay(Input.mousePosition); RaycastHit hit; if (Physics.Raycast(ray, out hit, 100f, LayerMask.GetMask("Terrain"))) { Vector3 placePosition = hit.point; if (Input.GetMouseButtonDown(0)) { HexTile tile = GetTileAtMousePosition(); if (tile != null) { if (tile.IsEmpty) { HexTile.MaterialEnum material = (terrain.TileCount < 9) ? HexTile.MaterialEnum.Grass : HexTile.MaterialEnum.Rock; terrain.SetTile(tile.tilePosition, material); SetExpansionMode(false); } } } } } else { if (Input.GetMouseButtonDown(0)) { Ray ray = camera.ScreenPointToRay(Input.mousePosition); RaycastHit hit; if (Physics.Raycast(ray, out hit, 100f)) { Goat goat = hit.collider.gameObject.GetComponentInParent <Goat>(); if (goat != null && goats.Contains(goat)) { // consume the goat player.energy += PlayerStats.potentialEnergyGoat; overlayController.SetEnergyValue(player.energy); // using the single dead function here // may want to also have a sacrifice animation goat.GotDead(); } Cow cow = hit.collider.gameObject.GetComponentInParent <Cow>(); if (cow != null && cows.Contains(cow)) { // consume the cow player.energy += PlayerStats.potentialEnergyCow; overlayController.SetEnergyValue(player.energy); // kill the cow cow.GotDead(); } Wolf wolf = hit.collider.gameObject.GetComponentInParent <Wolf>(); if (wolf != null && wolves.Contains(wolf)) { // consume the cow player.energy += PlayerStats.potentialEnergyWolf; overlayController.SetEnergyValue(player.energy); // kill the cow wolf.GotDead(); } } } } } }
private void UpdateHunger() { hunger -= hungerRate * Time.deltaTime; if (hunger < hungerEatThreshold) { if (eatingGoat != null) { if (!SceneManager.Instance.GoatExists(eatingGoat)) // was already eaten { eatingGoat = null; } else { Vector3 position = transform.position; Vector3 tilepos = eatingTile.center; float distance = Vector3.Distance(position, tilepos); if (distance < eatingDistance) { animator.Play("Eat"); animator.speed = 1f; hunger = 1f; eatingGoat.GotDead(); pathable.StopPathing(); } else if (pathable.stopped) { eatingTile = null; } } } else { //HexTile tile = SceneManager.Instance.terrain.FindNearestGrass(transform.position); eatingGoat = SceneManager.Instance.FindNearestGoat(transform.position); // wolves only eat goats. Cows give them tummy aches. if (eatingGoat != null) { Vector2Int tilePosition = eatingGoat.pathable.GetTilePosition(); eatingTile = SceneManager.Instance.terrain.GetTile(tilePosition); if (eatingTile == null || eatingTile.IsEmpty) { eatingTile = null; eatingGoat = null; } else { pathable.PathTo(eatingTile.tilePosition); } } } } if (hunger < 0f) { status.SetHungerValue(0f); GotDead(); } else { status.SetHungerValue(hunger); } }
public void DrawGrid() { float outerRadius = tileSize; float innerRadius = outerRadius * 0.866025404f; // thanks catlike coding https://catlikecoding.com/unity/tutorials/hex-map/part-1/ Vector3[] corners = { new Vector3(0f, 0f, outerRadius), // +z (top) new Vector3(innerRadius, 0f, 0.5f * outerRadius), // +x, +z new Vector3(innerRadius, 0f,-0.5f * outerRadius), // +x, -z new Vector3(0f, 0f, -outerRadius), // -z (bottom) new Vector3(-innerRadius, 0f,-0.5f * outerRadius), // new Vector3(-innerRadius, 0f, 0.5f * outerRadius), new Vector3(0f, 0f, outerRadius) }; tilesByTriangleIndex.Clear(); vertices.Clear(); triangles.Clear(); colours.Clear(); int vertexIndex = 0; int maxTiles = tiles.Length; Vector2Int[] cornerref; // after the map grows, this is used to maintain tile coordinates if (calibrationTile != null) { //get zero tile int z = 0; int x = 0; //cornerref = (z % 2 == 1) ? cornerrefEven : cornerrefOdd; HexTile tile = tiles[z * tilesW + x]; float xoffset = (z % 2 == 0) ? 0f : innerRadius; Vector3 center = new Vector3(x * innerRadius * 2f + xoffset, 0, z * outerRadius * 1.5f); for (z = 0; z < tilesH; z++) { cornerref = (z % 2 == 1) ? cornerrefEven : cornerrefOdd; for (x = 0; x < tilesW; x++) { tile = tiles[z * tilesW + x]; if (tile == calibrationTile) { // then make the hex xoffset = (z % 2 == 0) ? 0f : innerRadius; Vector3 calibrationCenter = new Vector3(x * innerRadius * 2f + xoffset, 0, z * outerRadius * 1.5f); offset += center - calibrationCenter; } } } calibrationTile = null; } for (int z = 0; z < tilesH; z++) { cornerref = (z % 2 == 1) ? cornerrefEven : cornerrefOdd; for (int x = 0; x < tilesW; x++) { HexTile tile = tiles[z * tilesW + x]; // first, should do null check // and then check if we should draw empty cells if (tile == null || (tile.IsEmpty && drawEmpty == false)) { continue; } // then make the hex float xoffset = (z % 2 == 0) ? 0f : innerRadius; Vector3 center = new Vector3(x * innerRadius * 2f + xoffset, tile.height, z * outerRadius * 1.5f) + offset; for (int cornerIndex = 0; cornerIndex < 6; cornerIndex++) { Vector3 p0 = center; Vector3 p1 = center + corners[cornerIndex]; Vector3 p2 = center + corners[cornerIndex + 1]; Vector2Int corner1Ref = cornerref[cornerIndex * 2]; Vector2Int corner2Ref = cornerref[cornerIndex * 2 + 1]; int adjacent1Index = (corner1Ref.y + z) * tilesW + x + corner1Ref.x; int adjacent2Index = (corner2Ref.y + z) * tilesW + x + corner2Ref.x; float height = tile.height; int numAdjacentTiles = 1; if (adjacent1Index > 0 && adjacent1Index < maxTiles && tiles[adjacent1Index] != null) { numAdjacentTiles++; height += tiles[adjacent1Index].height; } if (adjacent2Index > 0 && adjacent2Index < maxTiles && tiles[adjacent2Index] != null) { numAdjacentTiles++; height += tiles[adjacent2Index].height; } height /= numAdjacentTiles; p1.y = height; int cornerIndexP1 = cornerIndex + 1; if (cornerIndexP1 == 6) { corner1Ref = cornerref[0]; corner2Ref = cornerref[1]; } else { corner1Ref = cornerref[cornerIndexP1 * 2]; corner2Ref = cornerref[cornerIndexP1 * 2 + 1]; } adjacent1Index = (corner1Ref.y + z) * tilesW + x + corner1Ref.x; adjacent2Index = (corner2Ref.y + z) * tilesW + x + corner2Ref.x; height = tile.height; numAdjacentTiles = 1; if (adjacent1Index > 0 && adjacent1Index < maxTiles && tiles[adjacent1Index] != null) { numAdjacentTiles++; height += tiles[adjacent1Index].height; } if (adjacent2Index > 0 && adjacent2Index < maxTiles && tiles[adjacent2Index] != null) { numAdjacentTiles++; height += tiles[adjacent2Index].height; } height /= numAdjacentTiles; p2.y = height; vertices.Add(p0); vertices.Add(p1); vertices.Add(p2); triangles.Add(vertexIndex++); triangles.Add(vertexIndex++); triangles.Add(vertexIndex++); Color color = new Color(((int)tile.material) / 255f, 0, 0); colours.Add(color); colours.Add(color); colours.Add(color); // store info in the tile for later tile.center = center; tile.tilePosition = new Vector2Int(x, z); tilesByTriangleIndex.Add(vertexIndex / 3, tile); } } } mesh.Clear(); mesh.SetVertices(vertices); mesh.SetTriangles(triangles, 0); mesh.SetColors(colours); mesh.RecalculateNormals(); meshFilter.sharedMesh = mesh; meshRenderer.sharedMaterial = material; meshCollider.sharedMesh = mesh; }