【Unity】カードのレア度やステージのクリア率を表す星を表示

カードのレア度やステージのクリア率を表す星を表示

カードのレアリティや、ステージのクリア率を表す星のUIをコントロール。
0.5単位を表現するAパターンと、更に細かい単位まで表現するBパターンを用意。

GIMPでの、星の画像素材の作り方もあります。

サンプル動画

【Aパターン】0.5単位で表現

【Bパターン】もっと細かく表現

前提

以下の、2パターンを用意しています。
Aパターンはシンプル版、Bパターンは高機能版といった感じです。

  • 【Aパターン】星(半分)を別の画像として扱う。0.25~0.74までを星(半分)として丸める。
  • 【Bパターン】星画像をImage Type:Filledに設定して、画像の欠け具合を変更する。

星の画像素材を用意

手持ちのアセットから用意するか、自作する。
もしくは、↓の画像を使っても良い。

【ダウンロード】星の画像素材(簡易)

  • 圧縮済み
  • ライセンス:CC0

黄色星(フル)

【CC0】黄色星の画像素材

黄色星(半分)

*Aパターンでのみ使用。

【CC0】黄色星(半分)の画像素材

一応、白色も。

【GIMP】星の画像素材の作り方

  • *GIMPの言語設定:日本語
  1. キャンバスを任意の大きさに設定(希望する星画像より大きめに)。
  2. 上部メニュー -> フィルター -> 下塗り -> シェイプ(Gfig)を選択。
  3. 出現したダイアログ -> 上部メニューの下のアイコン群 -> 左から七番目の「星の作成」を選択。
    1. ツールオプション -> サイズ:5
    2. 輪郭を描画する:任意(有効にすると、現在のブラシで輪郭が追加される)
    3. 塗りつぶし:色で塗りつぶす
    4. 色:黄色
    5. グリッドにスナップ:有効
    6. 画像部分で中心から上にドラッグし、適度な大きさの星作成。
  • シェイプ(Gfig)フィルターでのグリッドの設定は、30に固定されている模様。

Unityへ画像をインポート

  1. Projectウィンドウ -> 任意のフォルダに、画像をドラッグ&ドロップしてインポート。
  2. 【3Dモードの場合】インスペクター -> Texture Typeを、Sprite (2D and UI)に変更。
    (2Dモードの場合は、デフォルトでSprite (2D and UI)になっている)

ざっくりした手順

  1. Canvas作成。
    1. UI Scale Mode:Scale With Screen Sizeに設定。
    2. Reference Resolution:(1920, 1080)等に設定。
  2. Canvas下に、空のオブジェクト作成、「Stars」と命名。
    1. Horizontal Layout Groupをアタッチ。
      1. Child Alignment:Middle Centerに設定。
    2. Content Size Fitterをアタッチ。
      1. Horizontal Fit:Preferred Sizeに設定。
      2. Vertical Fit:Preferred Sizeに設定。
  3. Image作成、”Star”と命名。
    1. 【Bパターン】Image Type:Filled
    2. 【Bパターン】Fill Method:Horizontal
    3. 新規スクリプトをアタッチ、後述のStarのコードを記述。
    4. インスペクターから、各変数へStar自らをドラッグ&ドロップ。
    5. プレハブ化。
  4. 空のオブジェクトを作成、「UIManager」と命名。
    1. 新規スクリプトをアタッチ、後述のUIManagerのコードを記述。
    2. インスペクターから、各変数へ対象のオブジェクトをドラッグ&ドロップ。

詳細な手順

Canvas作成

  1. 上部メニュー -> GameObject -> UI -> Canvasを作成。
  2. インスペクター -> Canvas Scalerコンポーネントを設定。
    1. UI Scale Mode:Scale With Screen Size
    2. Reference Resolution:(X 1920, Y 1080)

Stars(整列用の親オブジェクト)を作成

  1. ヒエラルキー -> Canvasを選択。
  2. 上部メニュー -> GameObject -> Create Empty Childを選択、「Stars」と命名。
  3. インスペクター -> Add Component -> 「Horizontal Layout Group」を作成、続いて設定。
    1. Spacing:任意の値(星間の距離になる)
    2. Child Alignment:Middle Center
  4. インスペクター -> Add Component -> 「Content Size Fitter」を作成、続いて設定。
    1. Horizontal Fit:Preferred Size
    2. Vertical Fit:Preferred Size

Star(星本体)を作成

  1. 上部メニュー -> GameObject -> UI -> Imageを作成、「Star」と命名。
  2. 【Bパターン】インスペクター -> Imageコンポーネントを設定。
    1. 【Bパターン】Image Type:Filled
    2. 【Bパターン】Fill Method:Horizontal
  3. インスペクター -> Add Component -> New scriptを選択、「Star」と命名。
  4. 以下のコードを貼り付け。
  5. インスペクターで各種変数にオブジェクトを紐付けしておく。

【コード】Star

管理クラスで、星にアタッチされたコンポーネントを複数扱うので、このクラスにまとめている。


using UnityEngine;
using UnityEngine.UI;

public class Star : MonoBehaviour
{
//インスペクターから、各種コンポーネントを紐付け。
	public GameObject go;
	public RectTransform rt;
	public Image img;

	public bool isActive;

	public void SetActive(bool b)
	{
		isActive = b;
		go.SetActive(b);
	}
}

UIManager(星管理用オブジェクト)を作成

  1. 上部メニュー -> GameObject -> Create Emptyを選択、「UIManager」と命名。
  2. インスペクター -> Add Component -> New scriptを選択、「UIManager」と命名。
  3. 以下のコードを貼り付け。
  4. インスペクターで各種変数にオブジェクトを紐付けしておく。

【コード/Aパターン】UIManager

星の表示管理用クラス。
クラス名と合わせれば、任意の名前で良いです。


//使わなかった為、一応コメントアウト。
//using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;


//スクリプト名と一致していれば、UIManagerじゃなくて任意の名前で良い。
public class UIManager : MonoBehaviour
{

//インスペクターから、インポートした星の画像を紐付けておく。
	[SerializeField]
	Sprite starSpr;

//インスペクターから、インポートした星(半分)の画像を紐付けておく。
	[SerializeField]
	Sprite halfStarSpr;

//インスペクターから、"Stars"(Starの親オブジェクト)を紐付けておく。
	[SerializeField]
	Transform starsParentTf;

//インスペクターから、Starのプレハブを紐付けておく。
	[SerializeField]
	GameObject starPrefab;    

//Starクラスを保持。
	List<Star> starList = new List<Star>(StarCountMax);

//星数の上限。任意の値。
	static readonly int StarCountMax = 3;

//Starのサイズ。任意の値。
	Vector2 starSize = new Vector2(100.0f, 100.0f);
//HalfStarのサイズ。Xは、StarのXの半分。Yは同じ値で。
	Vector2 halfStarSize = new Vector2(50.0f, 100.0f);

//アクティブな最後尾の星のインデックス。
	int starEndIndex = -1;

	float remainder;



	void Awake()
	{
		InitializeStars();
	}


//星々の初期化。
	void InitializeStars()
	{
		for (int i = 0; i < StarCountMax; i++) {
			starList.Add(Instantiate(starPrefab, starsParentTf).GetComponent<Star>());
			starList[i].SetActive(false);
		}
	}

//星を表示したい時に呼ぶ。引数には表示したい星数(float型)を渡す。リセットを入れているので、後から星数の変更可能。
	void UpdateStars(float starCount)
	{
		ResetStars();

//星数のリミッター。
		if (StarCountMax < starCount)
			starCount = StarCountMax;

//starCountに応じて、星をアクティブ化。
		for (int i = 0; i < StarCountMax; i++) {
			starList[i].SetActive(i < starCount);
		}

//端数が0.25~0.74ならば、HalfStarの画像に差し替え。大きさも合わせる。
		remainder = starCount % 1.0f;
		if (0.25f <= remainder && remainder < 0.75f) {
			starEndIndex = Mathf.FloorToInt(starCount / 1.0f);
			starList[starEndIndex].img.sprite = halfStarSpr;
			starList[starEndIndex].rt.sizeDelta = halfStarSize;
		}
	}

//弄った星のインデックスを記録しておいて、その部分のみリセット。
	void ResetStars()
	{
		if (starEndIndex != -1) {
			starList[starEndIndex].img.sprite = starSpr;
			starList[starEndIndex].rt.sizeDelta = starSize;
		}
	}

}

【コード/Bパターン】UIManager


//使わなかった為、一応コメントアウト。
//using System.Collections;
using System.Collections.Generic;
using UnityEngine;
//using UnityEngine.UI;


//スクリプト名と一致していれば、UIManagerじゃなくて任意の名前で良い。
public class UIManager : MonoBehaviour
{
//インスペクターから、"Stars"(Starの親オブジェクト)を紐付けておく。
	[SerializeField]
	Transform starsParentTf;

//インスペクターから、Starのプレハブを紐付けておく。
	[SerializeField]
	GameObject starPrefab;    

	List<Star> starList = new List<Star>(StarCountMax);

//星数の上限。任意の値。
	static readonly int StarCountMax = 3;

//アクティブな最後尾の星のインデックス(fillAmountを変更して欠け具合を調整する星)。
	int starEndIndex = -1;

	float remainder;



	void Awake()
	{
		InitializeStars();
	}


	void InitializeStars()
	{
		for (int i = 0; i < StarCountMax; i++) {
			starList.Add(Instantiate(starPrefab, starsParentTf).GetComponent<Star>());
			starList[i].SetActive(false);
		}
	}

	void UpdateStars(float starCount)
	{
		ResetStars();

		if (StarCountMax < starCount)
			starCount = StarCountMax;

		for (int i = 0; i < StarCountMax; i++) {
			starList[i].SetActive(i < starCount);
		}

//1で割った余りを、fillAmountに入れて星の欠け具合に適用している。
		remainder = starCount % 1.0f;
		if (0 < remainder) {
			starEndIndex = Mathf.FloorToInt(starCount / 1.0f);
			starList[starEndIndex].img.fillAmount = remainder;
		}
	}

	void ResetStars()
	{
		if (starEndIndex != -1) {
			starList[starEndIndex].img.fillAmount = 1.0f;
		}
	}

}

タイトルとURLをコピーしました