カテゴリー別アーカイブ: Unity

【Unity UI】UI要素の幅を固定にする方法

temp

水平レイアウト(Horizonral Layout)を配置し、そこに2つのUI要素(この場合は、左に Input Field、右にスライダー)を入れると、上図のように横幅が均等になる。
左の要素の幅を固定にし、ウィンドウ幅が変化した場合は、スライダー幅だけが変化するようにしたい。
この方法がなかなかわからなかったが、いろいろググッてやっと判明したので、ここに記述しておく。

まずは固定にしたい要素を選び、インスペクタで【Add Component】を選び、Layout Element, Content Size Filter を追加する。
そして、前者で min Width を、後者で Horizontal Fit:MinSize を選ぶ。

temp

これで、要素は固定幅になるのだが、下図のように余分な余白が出来てしまう。

temp

余白を無くすためには、右側の要素にも Layout Element を Add Component し、Flexible Width に 100 などの大きな値を設定するとよい。

temp

以上で、下図のように左側の要素幅だけを固定にできたぞ。

temp
 

【Unity】複数の UI.Button を画面横幅いっぱいに並べる方法

1. GameObject > UI > Canvas メニューを選び、キャンパスを作成する(既に作成済みであれば省略可)。
2. Canvas 選択状態で、GameObject > Create Empty Child メニューを選び、空の GameObject を作成する。
3. インスペクタで、Rect Transform のアイコン部分をクリックし、左右ストレッチを選ぶ。href=”http://vivi.dyndns.org/wp/wordpress/wp-content/uploads/2015/11/temp10.png”>temp
下図のように、上部で、横幅いっぱいのエリアが作成される。

temp

4. インスペクタで 【Add Component】を押し、Layout > Horizonral Layout Group を選ぶ

temp

5. あとは並べたいUI要素をクリエイトし、GameObject の子要素にする

temp

そうすると、下図のように、ボタン等のUI要素を横いっぱいにレイアウトすることができるぞ。

temp

【Unity パーティクル】パーティクルを自前の画像に置き換える

画像を Assets ディレクトリに置き、インスペクタで Texture Type を「Sprite (2D or UI)」にします。

temp

マテリアルを作成し、先の画像をドラッグして Albedo 部分にドロップします。

temp

マテリアルのシェーダを Particle > Alpha Blended にします。

temp

パーティクルのレンダーモジュールを開き、Material のところに先に作ったマテリアルをドロップします。

temp

以上で、下図のように、パーティクル形状が指定画像になります。

temp

【Unity パーティクル】パーティクル形状を変更

temp

上図のように、パーティクルをインスペクタで参照し、Renderer > Particle Mode を「stretched Billboard」にすると、パーティクルを移動方向に細長くすることができるぞ。

その長さは Length Scale で調整できる。デフォルトは 2 だが、例えば 20 に設定し、Shape を球にすると、下図のように、フレアみたいでなんかかっちょいいパーティクルを生成できるぞ。

temp

【Unity C# スクリプト】マウスドラッグ・ホイールでメインカメラ位置制御

マウス操作でメインカメラの位置を制御可能にし、好きな角度から好きな倍率でシーンを見ることができるようにしてみよう。
そのためには、まずメインカメラの位置を球座標系で表すことにする。

public class ScrCamera : MonoBehaviour {
    public Vector3 m_target;    //   ターゲット位置
    public float m_distance;    //  ターゲット位置からの距離
    public float m_latitude;    //  緯度(上から見下ろしている場合: > 0)、[-90, +90]
    public float m_longitude;   //  経度(Z軸+方向から見ている場合:== 0)、Y軸+方向からみて時計回り、[0, 380)
    .....
}

コードは上記のようになる。
メインカメラが中央に捉えるターゲットの位置と、そこからの距離、緯度・経度(球座標系)をメンバ変数として保持する。

上記のデータが更新された場合、updateCamera() が呼ばれ、メインカメラの位置・方向が設定される。

    //  カメラ位置、向きを設定
    void updateCamera()
    {
        float y = m_distance * Mathf.Sin(m_latitude * Mathf.Deg2Rad);
        float t = m_distance * Mathf.Cos(m_latitude * Mathf.Deg2Rad);
        float x = t * Mathf.Sin(m_longitude * Mathf.Deg2Rad);
        float z = t * Mathf.Cos(m_longitude * Mathf.Deg2Rad);
        Camera.main.transform.position = new Vector3(x, y, z) + m_target;
        Camera.main.transform.LookAt(m_target);
    }

Mathf.Deg2Rad は、デグリーをラジアンに変換するための定数だ。
カメラの位置は、球座標で計算した変位にターゲット座標を加え、メインカメラの transform.position に代入している。
カメラの向きは LookAt(目標位置) で設定している。

このように Unity スクリプトには必要な機能がちゃんと用意されており、便利だなーと感心させられる。

これで、準備が整ったので、Start() で以下のようにカメラ位置・向きを初期化しておく。

    void Start () {
        m_target = new Vector3(0, 0, 0);
        m_distance = 5;
        m_latitude = 30;
        m_longitude = 45;
        updateCamera();
    }

カメラ初期位置などは適当に決めている。

次に、カメラ位置の更新だが、まずは簡単なマウスホイールによる拡大縮小から。
ターゲットとカメラの距離(m_distance)を増加させると縮小、減少させると拡大になるので、ホイールの回転を検知したら、増加・減少させるようにする。

    void Update()
    {
        float mouseWheelScroll = Input.GetAxis("Mouse ScrollWheel");
        if (mouseWheelScroll != 0)
        {
        	m_distance -= mouseWheelScroll*4;
        	if( mouseWheelScroll < 0 )
        		m_distance *= 1.1f;
        	else
        		m_distance /= 1.1f;
            if ((m_distance -= mouseWheelScroll*4) < 1)
                m_distance = 1;
            else if (m_distance > 1000)
                m_distance = 1000;
            updateCamera();
        }
        ....
    }

【Unity C# スクリプト】GUILayout で GUI コンポーネントを自動レイアウト

void OnGUI() 関数を定義したスクリプトを Canvas などにアタッチすると、GUILayout を使った自動レイアウトを使用することができるぞ。

GUILayout.BeginArea() でエリアを作成し、GUILayout.EndArea() で囲まれる部分にボタンなどのUIオブジェクトを配置していく。
以下は、2つのボタンを持つUIの例だ。

    void OnGUI() {
        GUILayout.BeginArea(new Rect(10, 10, 100, 100));
            GUILayout.Button("Click me");
            GUILayout.Button("Or me");
        GUILayout.EndArea();
    }

temp

もっと複雑なレイアウトにしたい場合は、BeginHorizontal、BeginVertical、BeginScrollView で入れ子エリアを作ることもできるぞ。

【Unity C# スクリプト】UI.Text に文字を設定

Hierarchy の Create をクリックして表示されるメニューから UI > Text を選び、Text オブジェクトを配置する。

temp

下図の様に、Canvas が自動的に作成され、その子オブジェクトとして Text オブジェクトが作成される。

temp

Project の Create を押し、C# スクリプトファイルを作成し、適当なコントロールオブジェクト(例えばメインカメラ)にアタッチする。

スクリプトの最初に using UnityEngine.UI; 文を追加し、GameObject  型の public 変数を追加する。
Unity エディタでアタッチされたオブジェクトをインスペクタで参照し、この public 変数を当該テキストオブジェクトに紐付ける。

using UnityEngine.UI;
....
public class ScriptName : MonoBehaviour {
    public GameObject uiText;
    .....
}

Text コンポーネントは uiText.GetComponent() で取得できるので、Text の text メンバ変数を参照・更新したり、他のメンバ関数をコールすることが可能。

    Debug.Log(uiText.GetComponent().text);  // 現テキストをコンソールに表示
    uiText.GetComponent().text = "hoge hoge";  // テキストを変更

 

【Unity C# スクリプト】オブジェクトを動的に生成

手順は以下の通り

1. 生成したいオブジェクトのプレファブを作成
2. オブジェクトを動的生成するスクリプトを作成し、なんらかのコントールオブジェクトにアタッチ
3. スクリプトのコードは以下のような感じ

public class scr_gameObject : MonoBehaviour {
  public Transform prefab;
  void Update () {
    if( Input.GetKey("space") ) {
      Instantiate(prefab, new Vector3(0f, 10f, 0f), Quaternion.identity);
    }
  }
}

最初にプレファブオブジェクト(への参照)を宣言する。
この変数と実際のプレファブとの紐付けは Unity エディタで行なう。

temp

注意点としては、スクリプトではなく、コントロールオブジェクトをインスペクタで見て、そこの prefab にドロップするという点だ。
スクリプトをインスペクターでみても prefab が表示されるが、そこにドロップしても期待したようには動作しない。

あとは、update() でキーが押されたときなどに、Instantiate() を用いて、プレファブからオブジェクトを生成する。
第2引数は生成位置、第3引数は回転行列を指定する。
回転しない場合は、例の用に「Quaternion.identity」を指定する。