首页 > 解决方案 > Unity 2D Tilemap Custom Hexagonal Rule Tile

问题描述

我正在寻找一种方法来创建一种新型的六边形规则瓷砖来做一些相当简单和具体的事情。我想创建一个能够根据与之相邻的其他类型的六边形图块自动选择精灵的十六进制规则图块。默认的六边形规则图块允许您在给定图块的每一侧都以相同的图块类型为边界时指定精灵,但这对于我的目的来说是不够的。

我最终想要的是创建一个海岸图块,它将检测哪些边与海洋图块接壤,并据此选择正确的十六进制精灵。像这样,但能够指定海洋瓷砖,而不仅仅是绿色箭头所示的瓷砖类型:

海岸瓷砖示例

我可以在他们的 github repo 中看到 Unity 的六边形规则图块的默认代码,但不知道如何完全覆盖它: https ://github.com/Unity-Technologies/2d-extras/blob/master/Runtime/Tiles /HexagonalRuleTile/HexagonalRuleTile.cs

这是 Unity 中一个相对较新的主题,但我们将不胜感激任何帮助或指导。

标签: c#unity3d

解决方案


好的,经过一些深入的谷歌搜索和反复试验后发现了这一点。我所需要的只是这个覆盖 RuleMatch 方法的继承类。希望这对其他人有用。

using System;
using UnityEngine;
using UnityEngine.Tilemaps;

[Serializable]
[CreateAssetMenu(fileName = "CoastHexagonTile", menuName = "Tiles/CoastHexagonTile")]
public class CoastHexagonTile : HexagonalRuleTile<CoastHexagonTile.Neighbor>
{
    public bool isOcean;
    public bool isCoast;

    public class Neighbor : TilingRule.Neighbor
    {
        public const int IsOcean = 3;
        public const int IsNotOcean = 4;
        public const int IsCoast = 5;
        public const int IsNotCoast = 6;
    }

    /// <summary>
    /// Checks if there is a match given the neighbor matching rule and a Tile.
    /// </summary>
    /// <param name="neighbor">Neighbor matching rule.</param>
    /// <param name="other">Tile to match.</param>
    /// <returns>True if there is a match, False if not.</returns>
    public override bool RuleMatch(int neighbor, TileBase tile)
    {
        var other = tile as CoastHexagonTile;
        switch (neighbor)
        {
            case Neighbor.IsOcean:
                return other && other.isOcean;
            case Neighbor.IsNotOcean:
                return other && !other.isOcean;
            case Neighbor.IsCoast:
                return other && other.isCoast;
            case Neighbor.IsNotCoast:
                return other && !other.isCoast;
        }
        return base.RuleMatch(neighbor, tile);
    }
}

编辑:不幸的是,由于某种原因,并非所有规则图块都遵守规则。我正在以编程方式在大地图上设置每个图块,我想知道这是否基本上是原因。

附加编辑:好的,我发现为了正确渲染图块,需要调用 Tilemap.RefreshAllTiles() 方法。我认为这只有在我正在做的时候在运行时移动并以编程方式设置瓷砖时才是正确的。


推荐阅读