注目キーワード

UnityにてiPhoneX対応・NGUIのUIAnchorにSafeAreaの補正処理を入れてみた

とりあえず、NGUIのUIAnchorについてSafeAreas対応ができたのでメモ。

他にも、SafeAreasとして以下の対応が必要になるが、この記事ではUIAnchorの対処方法を記載します。

 

必要になること:

・UIRectのAnchor

・UIScrollViewの表示範囲の調整(Anchorの基準が変化するためUI調整が必要になる)

 

前提条件:

この記事は、以下のことを前提に話を進めます。

 

・Unity5.6.6を使って開発しています。

・iOSSafeAreasPluginをダウンロードしてインポートしていること

 

Pluginのダウンロードサイト

https://bitbucket.org/p12tic/iossafeareasplugin/src

 

・OSはiOSのみ考慮しています。

 

 

ソースコード

まずは、ソースコードから公開します。

 

セーフエリアの取得

SafeAreaScreen.cs

このソースコードは、主にセーフエリアの取得を担当しています。

UnityエディタでスクリーンサイズをiPhoneXと同じサイズ(1125×2436)に設定すると、Unity Player上でもデバッグできます。

 

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using System.Runtime.InteropServices;

public class SafeAreaScreen  {

#if UNITY_IOS
	[DllImport("__Internal")]
	private extern static void GetSafeAreaImpl(out float x, out float y, out float w, out float h);
#endif

	static public Rect GetSafeArea()
	{
		float x, y, w, h;

		//初期値設定
		x = 0;
		y = 0;
		w = Screen.width;
		h = Screen.height;

#if UNITY_IOS && !UNITY_EDITOR
		//iOSSafeAreasPluginを呼び出す
		GetSafeAreaImpl(out x, out y, out w, out h);

#elif UNITY_ANDROID && !UNITY_EDITOR
		//Androidの縦長端末対応が必要になったときのために

#else


		//UnityエディタでiPhoneXのテストできるように値を設定する
		if(Screen.width == 1125 && Screen.height == 2436 ){
			y = 102;
			h = 2202;
		}

#endif
		return new Rect(x, y, w, h);
	}

	static public int GetTopOffsetY(){
		int offset = 0;

		//画面の高さとセーフエリアの高さの差分
		Rect screenSize = GetSafeArea();

		if (Screen.height != screenSize.height) {
			offset = Screen.height - (int)screenSize.height - (int)screenSize.y;
		}

		return offset;
	}

	static public int GetBottomOffsetY(){
		int offset = 0;

		//セーフエリアのyの位置取得
		Rect screenSize = GetSafeArea();

		if (Screen.height != screenSize.height) {
			offset = (int)screenSize.y;
		}

		return offset;
	}

}

 

NGUIのSafeArea

NguiSafeAreaPatch.cs

SafeAreaScreen.csで取得したセーフエリアを元にAnchorの位置を調整します。

 

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class NguiSafeAreaPatch : MonoBehaviour {

	void Awake()
	{
		// UIAnchorを使ってAnchorを設定している場合
		UIAnchor anchor = gameObject.GetComponent();
		if(anchor != null){

			//offsetの値を取得する
			SetUIAnchorOffset(anchor);

			return;
		}

		// UIRectをAnchorを使っている場合
		UIRect rect = gameObject.GetComponent();
		if (rect != null) {
			//現在,NGUIのソースコードを解析中
			//完成しだい公開予定
			return;
		}
	}

	private void SetUIAnchorOffset(UIAnchor anchor){

		//現在のoffsetを取得する
		Vector2 nowOffset = anchor.pixelOffset;

		//TOP側の補正値取得
		int topCorrectionOffset = SafeAreaScreen.GetTopOffsetY ();

		//Bottom側の補正値取得
		int bottomCorrectionOffset = SafeAreaScreen.GetBottomOffsetY ();

		switch (anchor.side) {

			case UIAnchor.Side.Top:
			case UIAnchor.Side.TopLeft:
			case UIAnchor.Side.TopRight:
				anchor.pixelOffset.Set(nowOffset.x, nowOffset.y - topCorrectionOffset);

			break;

			case UIAnchor.Side.Bottom:
			case UIAnchor.Side.BottomLeft:
			case UIAnchor.Side.BottomRight:
				anchor.pixelOffset.Set(nowOffset.x, nowOffset.y + bottomCorrectionOffset);			
			break;


		}
		
	}



}

 

使い方は、このソースコードをUIAnchorがアタッチされているゲームオブジェクトにアタッチするだけ。

 

 

 

ソース内でやっていることは、動作環境がiPhoneXと判定したら、スクリーンとセーフエリアの高さの差分を計算して、差分の分ゲームオブジェクトを下げます。

差分の値は、UIAnchorの「Pixel Offset」に代入されます。

 

ソースコードを反映させた結果

NguiSafeAreaPatch.csをUIAnchorにアタッチさせた結果を記載します。

 

■反映前

 

■反映後

その結果、セーフエリアを基準にすることができました。

 

 

これにてUIAnchorについてはSafeAreaの対処ができました。

しかし、ほかにも「UIRectのAnchor」に対してもSafeAreas対応があります。対応が終わり次第、随時記事に追加していきます。