unity > ラジオボタンを選択することで表示ウィンドウを切り替える実装

```txt:動作確認
Unity 5.1.2-f1 on MacOS X 10.8.5
```

ラジオボタンを選択した時に、それぞれに対応するウィンドウを表示したい。

## 実装
http://qiita.com/7of9/items/26fa124f49722ca8c63f
にて実装したラジオボタンを用意する。

ラジオボタンのON,OFFの検知は以下のものを使う。
http://qiita.com/7of9/items/05304886153123a0da2d

ウィンドウの表示・非表示は以下のものを使う。
http://qiita.com/7of9/items/95813013d0e18eb54a95

## Hierarchy

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/011c9151-5685-f445-ac29-be5ba1fc66d0.jpeg)

Panel1..4はウィンドウ。 SelP1..4はラジオボタン。
PanelDisplayController には上記実装のスクリプトが関連付けられている。

PanelDisplayControlスクリプトのpublic変数には以下の図のように関連付けをしている。

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/76a7191e-0e81-527f-110a-e3d2543f5dce.jpeg)

## code

[v0.2 @ github](https://github.com/yasokada/unity-150905-dynamicDisplay/releases/tag/v0.2)

実装は以下の通り。

- Start()において、各Panelの元々のサイズを取得。(そのため、編集保存時には各PanelがActiveになっていることが必要)
- ToggleValueChanged()において、変更があったSelPxを検知して、表示・非表示を変更。

```csharp
using UnityEngine;
using System.Collections;
using UnityEngine.UI;

/*
 * v0.2 2015/09/06
 *   - add sample UI components in each panel
 * v0.1 2015/09/05
 *   - show/hide panels
 */

public class PanelDisplayControl : MonoBehaviour {

	public GameObject PageSelect;
	public GameObject PanelGroup;

	private Vector2[] orgSize;

	void Start() {
		orgSize = new Vector2[4];
		int idx=0;

		foreach (Transform child in PanelGroup.transform) {
			orgSize[idx].x = child.gameObject.GetComponent<RectTransform>().rect.width;
			orgSize[idx].y = child.gameObject.GetComponent<RectTransform>().rect.height;

			bool isOn = getIsOn (idx + 1);
			DisplayPanel (idx + 1, isOn);

			idx++;
		}

	}

	bool getIsOn(int idx_st1) {
		Toggle selected = null;
		string name;
		foreach (Transform child in PageSelect.transform) {
			name = child.gameObject.name;
			if (name.Contains(idx_st1.ToString())) { // e.g. "SelP1", "SelP2"...
				selected = child.gameObject.GetComponent(typeof(Toggle)) as Toggle;
				break;
			}
		}
		return selected.isOn;
	}

	void DisplayPanel(int idx_st1, bool doShow)
	{
		GameObject panel = GameObject.Find ("Panel" + idx_st1.ToString ());
		if (panel == null) {
			return;
		}

		RectTransform rect = panel.GetComponent (typeof(RectTransform)) as RectTransform;
		Vector2 size = rect.sizeDelta;
		if (doShow) {
			size.x = orgSize[idx_st1 - 1].x;
			size.y = orgSize[idx_st1 - 1].y;
		} else {
			size.x = 0;
			size.y = 0;
		}
		rect.sizeDelta = size;
	}

	public void ToggleValueChanged(int idx_st1) {
		bool isOn = getIsOn (idx_st1);
		DisplayPanel (idx_st1, isOn);
		Debug.Log (isOn.ToString ());
	}

}
```

## 使用例

ラジオボタンでウィンドウを切り替えられる。

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/63152df7-75e3-c23c-9e8f-e18837954700.jpeg)

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/93b7dedc-6ad2-bc94-f43f-1869d130e067.jpeg)

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/b633daba-1c73-8e4f-2be0-f7ddb80fcd81.jpeg)

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/3b454cad-1683-50e2-5ac8-284e24baa986.jpeg)

非表示になったウィンドウ(Panel)についても値そのものは読み取れ、前の状態も保っているのがいい。

限られた画面枠内にたくさんの情報やコントロール部品を置いて表示切り替えしながら使うことができる。


http://makezine.jp/blog/2014/02/making-fun-mission-control-desk.html
をスマホで再現できる？

Deep Space 9のコントロールパネルを参考にするのもあり? 
http://www.lcars.org.uk/lcarstemplate.htm?Page=lcars_DS9_panels.htm


## v0.3 (タグを使用)

表示・非表示するPanelを探す時に、Panelの名前で探していたのがいまいちだった。
tag (TagP1, TagP3など)で対象を探すように変更した。

[v0.3 @ github](https://github.com/yasokada/unity-150905-dynamicDisplay/releases/tag/v0.3)

v0.3にて変わったのは以下。

```csharp
	void DisplayPanel(int idx_st1, bool doShow)
	{
		GameObject [] panels = GameObject.FindGameObjectsWithTag ("TagP" + idx_st1.ToString ());

		if (panels == null) {
			return;
		}

		foreach (GameObject panel in panels) {
			RectTransform rect = panel.GetComponent (typeof(RectTransform)) as RectTransform;
			Vector2 size = rect.sizeDelta;
			if (doShow) {
				size.x = orgSize [idx_st1 - 1].x;
				size.y = orgSize [idx_st1 - 1].y;
			} else {
				size.x = 0;
				size.y = 0;
			}
			rect.sizeDelta = size;
		}
	}

```

あとは元サイズ情報の扱いを改善すれば、複数のPanelを各ページに割り当てできる。


## v0.4 (各ページのパネル数制限を排除)
[v0.4 @ github](https://github.com/yasokada/unity-150905-dynamicDisplay/releases/tag/v0.4)

- 表示・非表示するPanel検索にTagを使用
- .sizeDeltaでなく.localScaleを使用 ([qiita](http://qiita.com/7of9/items/95813013d0e18eb54a95#localscale%E3%82%92%E4%BD%BF%E3%81%A3%E3%81%9F%E6%96%B9%E3%81%8C%E3%82%88%E3%81%84))

以上の変更により、ページごとの表示するPanel数に制限がなくなった。

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/bb98c590-75c9-d494-b065-4754669e2553.jpeg)

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/2ddcadc4-044e-1433-3e7c-77a5e5371108.jpeg)

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/e5657714-91df-0b87-0e67-382e9a80596d.jpeg)

![Main_unity_-_150905-dynamicDisplay_-_PC__Mac___Linux_Standalone__Personal_.jpg](https://qiita-image-store.s3.amazonaws.com/0/32870/14f6bf66-08c0-2c1f-2c65-ee432957f26c.jpeg)