我必须在Unity 3D中创建“滑动解锁”功能(就像iPhone锁定屏幕中的那个)。我尝试了以下几点:
第1部分 - 检测滑动
我可以使用以下代码检测滑动:
private bool couldBeSwipe = false;
private float minSwipeDistance = 14;
private float maxSwipeTime = 10;
private float comfortZone = 100;
private float startTime;
private Vector2 startPos;
const int SWIPE_NONE = 0;
const int SWIPE_UP = 1;
const int SWIPE_RIGHT = 2;
const int SWIPE_DOWN = 3;
const int SWIPE_LEFT = 4;
private int swipeDirection = SelectStageScene.SWIPE_NONE;
在void Update()
:
// Input
swipeDirection = SelectStageScene.SWIPE_NONE;
if (Input.touchCount > 0) {
Touch touch = Input.touches [0];
switch (touch.phase) {
case TouchPhase.Began:
couldBeSwipe = true;
startPos = touch.position;
startTime = Time.time;
break;
case TouchPhase.Moved:
if ((Mathf.Abs (touch.position.y - startPos.y) > comfortZone) && (Mathf.Abs (touch.position.x - startPos.x) > comfortZone)) {
couldBeSwipe = false;
}
break;
case TouchPhase.Ended:
float swipeTime = Time.time - startTime;
float swipeDistance = (touch.position - startPos).magnitude;
float deltaX = touch.position.x - startPos.x;
float deltaY = touch.position.y - startPos.y;
if (couldBeSwipe && (swipeTime < maxSwipeTime) && (swipeDistance > minSwipeDistance)) {
if (Mathf.Abs (deltaX) > comfortZone) {
float swipeDirectionY = Mathf.Sign(deltaX);
if (swipeDirectionY == 1) {
swipeDirection = SelectStageScene.SWIPE_RIGHT;
} else {
swipeDirection = SelectStageScene.SWIPE_LEFT;
}
}
if (Mathf.Abs (deltaY) > comfortZone) {
float swipeDirectionY = Mathf.Sign(deltaY);
if (swipeDirectionY == 1) {
swipeDirection = SelectStageScene.SWIPE_UP;
} else {
swipeDirection = SelectStageScene.SWIPE_DOWN;
}
}
} else if (swipeTime > maxSwipeTime) {
Debug.Log ("Too slow");
swipeDirection = SelectStageScene.SWIPE_NONE;
} else if (swipeDistance < minSwipeDistance) {
Debug.Log ("Too short");
swipeDirection = SelectStageScene.SWIPE_NONE;
} else if (!couldBeSwipe) {
Debug.Log ("Not a swipe");
swipeDirection = SelectStageScene.SWIPE_NONE;
} else {
swipeDirection = SelectStageScene.SWIPE_NONE;
}
break;
}
}
第2部分 - 移动纹理(带轴约束)
移动纹理的方法有多种,包括GUI.DragWindow()
,GUI.Box()
等。但没有一种方法可以直接移动Texture
。这是沿轴移动纹理的最简单方法。例如,仅限制其在X轴上的移动?
答案 0 :(得分:2)
关于使用Unity GUI,没有&#39;运动&#39;每次调用OnGUI(){}内部的GUI元素时,您都会不断地重绘或发送重绘消息,例如GUI.Button
如果你想使用OnGUI,我按照以下方式构建运动;
我已经塑造了你的功能,写了这堂课;
using UnityEngine;
using System.Collections;
public class SelectStageScene : MonoBehaviour {
// You'll want to set this;
public Texture2D screenTexture;
private float minSwipeDistance = 14;
private float maxSwipeTime = 10;
private float startTime;
private Vector2 startPos;
private Vector2 currentPos;
const int SWIPE_NONE = 0;
const int SWIPE_UP = 1;
const int SWIPE_RIGHT = 2;
const int SWIPE_DOWN = 3;
const int SWIPE_LEFT = 4;
private int swipeDirection = SelectStageScene.SWIPE_NONE;
private Vector2 screenTextureOffset = Vector2.zero;
private float fadeAlpha = 0f;
private float fadeSpeed = 1f; // How fast the texture fades after swipe.
public void Update() {
// If no swipe direction is set.
if ( swipeDirection == SelectStageScene.SWIPE_NONE ) {
// To fade back in after swipe (just to complete the loop)
if ( fadeAlpha > 0 ) {
fadeAlpha -= Time.deltaTime * fadeSpeed;
}
// Getting input
if ( Input.touchCount > 0 ) {
Touch touch = Input.touches [0];
switch ( touch.phase ) {
case TouchPhase.Began:
startPos = touch.position;
startTime = Time.time;
break;
case TouchPhase.Moved:
currentPos = touch.position;
break;
case TouchPhase.Ended:
screenTextureOffset = currentPos - startPos;
// By using swipe distance as a magnitude here, regardless of x or y axis, we'll be choosing a swipe direction.
// If we were only interested in X axis we would use screenTextureOffset.x instead of swipeDistance
if ( Time.time - startTime < maxSwipeTime && ( currentPos - startPos ).magnitude > minSwipeDistance ) {
// Find if we've moved more on the x-axis or y-axis.
if ( Mathf.Abs( screenTextureOffset.x ) > Mathf.Abs( screenTextureOffset.y ) ) {
// x-axis
if ( screenTextureOffset.x > 0 ) {
swipeDirection = SelectStageScene.SWIPE_RIGHT;
} else {
swipeDirection = SelectStageScene.SWIPE_LEFT;
}
} else {
// y-axis
if ( screenTextureOffset.y > 0 ) {
swipeDirection = SelectStageScene.SWIPE_UP;
} else {
swipeDirection = SelectStageScene.SWIPE_DOWN;
}
}
} else {
swipeDirection = SelectStageScene.SWIPE_NONE;
}
break;
}
} else {
screenTextureOffset *= 1 - Time.deltaTime * fadeSpeed;
}
} else {
// This fades the texture and moves it further in direction of swipe.
screenTextureOffset *= 1 + Time.deltaTime * fadeSpeed;
fadeAlpha += Time.deltaTime * fadeSpeed;
if ( fadeAlpha > 1 ) {
swipeDirection = SelectStageScene.SWIPE_NONE;
Debug.Log( "Finished swipe movement : " + swipeDirection );
}
}
}
public void OnGUI() {
GUI.color = Color.white - Color.black * fadeAlpha;
GUI.DrawTexture( new Rect( screenTextureOffset.x, screenTextureOffset.y, Screen.width, Screen.height ), screenTexture );
/*// Specific axis. Constraining visually leaves easy potential access later on.
if ( Mathf.Abs( screenTextureOffset.x ) > Mathf.Abs( screenTextureOffset.y ) ) {
// x-axis
GUI.DrawTexture( new Rect( screenTextureOffset.x, 0, Screen.width, Screen.height ), screenTexture );
} else {
// y-axis
GUI.DrawTexture( new Rect( 0, screenTextureOffset.y, Screen.width, Screen.height ), screenTexture );
}
*/
}
}