前回の続きです。
Tilemapからミニマップを作成してみた①
上記の画像を見ると、カメラのサイズに対してマップのサイズが小さく見えます。
これは背景(透明黒色の部分)が十分な大きさで作成されていないからです。
なので、テクスチャのサイズを少し大きくします。
1.MinMap.csを以下のように変更します。
public class MiniMap : MonoBehaviour
{
[SerializeField] Transform _grid;
[SerializeField] Image _image;
// マップの色
[SerializeField] Color _wallColor;
[SerializeField] Color _groundColor;
[SerializeField] Color _noneColor;
// 余白
[SerializeField] int _space = 20;
// マップ用テクスチャ
Texture2D _texture;
void Start()
{
Tilemap groundTilemap = _grid.Find("Ground").GetComponent<Tilemap>();
Tilemap wallTilemap = _grid.Find("Wall").GetComponent<Tilemap>();
// テクスチャ作成
Vector3Int size = new Vector3Int(wallTilemap.size.x + _space * 2, wallTilemap.size.y + _space * 2, wallTilemap.size.z);
_texture = new Texture2D(size.x, size.y, TextureFormat.ARGB32, false);
// こうしないと、画像がぼやける
_texture.filterMode = FilterMode.Point;
Vector3Int origin = new Vector3Int(wallTilemap.origin.x - _space, wallTilemap.origin.y - _space, wallTilemap.origin.z);
......
今はマップの後ろが不透明なので、例えばここに敵がいた場合見つけることができず、プレイヤーにストレスを与えることになります。
なのでマップの後ろを見えるようにします。
1.「MiniMap」の「None Color」をちょうどいい透明度にする
2.「MiniMap>Camera」の「Clear Flags」を「Depth Only」に変更する
現在はプレイヤーが動いてもマップは止まったままです。
これを、プレイヤーに合わせて描画内容が変わるようにします。
1.Standard Assetsをインポートする
Standard Assets
2.「MiniMap>Camera」に「FollowTarget」を追加し、設定を以下のように変更
1.プレイヤーオブジェクトの下に、マップ上で表示するSprite Rendererを作成し、設定を以下のように変更
今回のステージの壁は、3Grid使って表示しています。
ただこれをそのままマップ上で表示すると壁が太く見えるので、地面タイルに隣接している壁のみ表示するように変更します。
隣接しているか確認するのは、上下左右斜めの8方向です。
1.「MiniMap.cs」を以下のように変更
......
// 地面タイルが存在するか確認する方向
Vector3Int[] directions = new Vector3Int[]
{
new Vector3Int(-1, 0, 0), new Vector3Int(1, 0, 0), new Vector3Int(0, -1, 0), new Vector3Int(0, 1, 0),
new Vector3Int(-1, -1, 0), new Vector3Int(1, -1, 0), new Vector3Int(1, 1, 0), new Vector3Int(-1, 1, 0),
};
// テクスチャ座標ごとの色を求める
for (int y = 0; y < size.y; ++y)
{
for (int x = 0; x < size.x; ++x)
{
// Tilemapのグリッド座標
Vector3Int cellPos = new Vector3Int(origin.x + x, origin.y + y, 0);
// マップカラー
Color color = _noneColor;
// 壁タイルが存在する
if (wallTilemap.GetTile(cellPos) != null)
{
// 8方向のどこかに地面タイルが存在するかチェック
for (int i = 0; i < directions.Length; ++i)
{
if (groundTilemap.GetTile(cellPos + directions[i]) != null)
{
color = _wallColor;
break;
}
}
}
// 地面タイルが存在する
else if (groundTilemap.GetTile(cellPos) != null)
{
color = _groundColor;
}
_texture.SetPixel(x, y, color);
}
}
......
一応、最終的なMiniMap.csを書いておきます。
次は、一度確認した箇所だけ表示されるマップや、フロア単位で表示されるマップを作ろうと思います。
using UnityEngine;
using UnityEngine.Tilemaps;
using UnityEngine.UI;
public class MiniMap : MonoBehaviour
{
[SerializeField] Transform _grid;
[SerializeField] Image _image;
// マップの色
[SerializeField] Color _wallColor;
[SerializeField] Color _groundColor;
[SerializeField] Color _noneColor;
// 余白
[SerializeField] int _space = 20;
// マップ用テクスチャ
Texture2D _texture;
void Start()
{
Tilemap groundTilemap = _grid.Find("Ground").GetComponent<Tilemap>();
Tilemap wallTilemap = _grid.Find("Wall").GetComponent<Tilemap>();
// テクスチャ作成
int width = wallTilemap.size.x + _space * 2;
int height = wallTilemap.size.y + _space * 2;
Vector3Int size = new Vector3Int(width, height, wallTilemap.size.z);
_texture = new Texture2D(size.x, size.y, TextureFormat.ARGB32, false);
// こうしないと、画像がぼやける
_texture.filterMode = FilterMode.Point;
Vector3Int origin = new Vector3Int(wallTilemap.origin.x - _space, wallTilemap.origin.y - _space, wallTilemap.origin.z);
// 地面タイルが存在するか確認する方向
Vector3Int[] directions = new Vector3Int[]
{
new Vector3Int(-1, 0, 0), new Vector3Int(1, 0, 0), new Vector3Int(0, -1, 0), new Vector3Int(0, 1, 0),
new Vector3Int(-1, -1, 0), new Vector3Int(1, -1, 0), new Vector3Int(1, 1, 0), new Vector3Int(-1, 1, 0),
};
// テクスチャ座標ごとの色を求める
for (int y = 0; y < size.y; ++y)
{
for (int x = 0; x < size.x; ++x)
{
// Tilemapのグリッド座標
Vector3Int cellPos = new Vector3Int(origin.x + x, origin.y + y, 0);
// マップカラー
Color color = _noneColor;
// 壁タイルが存在する
if (wallTilemap.GetTile(cellPos) != null)
{
// 8方向のどこかに地面タイルが存在するかチェック
for (int i = 0; i < directions.Length; ++i)
{
if (groundTilemap.GetTile(cellPos + directions[i]) != null)
{
color = _wallColor;
break;
}
}
}
// 地面タイルが存在する
else if (groundTilemap.GetTile(cellPos) != null)
{
color = _groundColor;
}
_texture.SetPixel(x, y, color);
}
}
// テクスチャ確定
_texture.Apply();
// テクスチャをImageに適用
_image.rectTransform.sizeDelta = new Vector2(size.x, size.y);
_image.sprite = Sprite.Create(_texture, new Rect(0, 0, size.x, size.y), Vector2.zero);
// _imageをGridの中心に移動
Vector2 leftDownWorldPos = wallTilemap.CellToWorld(origin);
Vector2 rightUpWorldPos = wallTilemap.CellToWorld(origin + size);
_image.transform.position = (leftDownWorldPos + rightUpWorldPos) * 0.5f;
}
private void OnDestroy()
{
Destroy(_texture);
}
}
Crieitは誰でも投稿できるサービスです。 是非記事の投稿をお願いします。どんな軽い内容でも投稿できます。
また、「こんな記事が読みたいけど見つからない!」という方は是非記事投稿リクエストボードへ!
こじんまりと作業ログやメモ、進捗を書き残しておきたい方はボード機能をご利用ください。
ボードとは?
コメント