This repository has been archived on 2026-01-20. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
AW_2025/Assets/Scripts/CameraController/TouchInteraction.cs
2025-02-24 15:42:43 +09:00

287 lines
9.1 KiB
C#

using System;
using UnityEngine;
using UnityEngine.EventSystems;
using Vector2 = UnityEngine.Vector2;
using Vector3 = UnityEngine.Vector3;
namespace game4automation
{
//! Controls touch interaction during game4automation simulation / play mode
public class TouchInteraction : MonoBehaviour
{
[Header("Settings")] public bool EnableZoom = true;
public bool EnableRotation = true;
public bool EnableOneFingerPan = true;
public bool EnableTwoFingerPan = true;
public bool AllowTouchOverUI = false;
public bool EnableTilt = true;
public float MinRot = 0.1f;
public bool EnableTest = true;
public bool DebugLog = true;
[Header("Status")] public Vector3 Pan;
public float Zoom;
public float Rot;
public Vector3 Tilt;
public Vector2 FirstTouch;
public Vector2 SecondTouch;
public Vector2 ThirdTouch;
private bool _test = false;
private Vector2 _firstbefore;
private Vector2 _secondbefore;
private Vector2 _firstdeltapos;
private Vector2 _seconddeltapos;
private int _tapcount;
private float _doubleTapTimer;
public delegate void OneTouchPanDelegate(Vector2 pos, Vector2 pan);
public OneTouchPanDelegate oneTouchPanEvent;
public delegate void TwoTouchPanZoomRotDelegate(Vector2 pos, Vector2 pan, float zoom, float rot);
public TwoTouchPanZoomRotDelegate twoTouchPanZoomRotDelegate;
public delegate void ThreeTouchPanDelegate(Vector2 pos, Vector2 pan);
public ThreeTouchPanDelegate threeTouchPanDelegate;
public delegate void DoubleTouchDelegate(Vector2 pos);
public DoubleTouchDelegate doubleTouchDelegate;
// Update is called once per frame
void Update()
{
// Double touch
if (Input.touchCount == 1 && Input.GetTouch(0).phase == TouchPhase.Began)
{
_tapcount++;
}
if (_tapcount > 0)
{
_doubleTapTimer += Time.deltaTime;
}
//Double Tap Detected
if (_tapcount >= 2)
{
_doubleTapTimer = 0.0f;
_tapcount = 0;
if (doubleTouchDelegate != null)
{
doubleTouchDelegate(Input.GetTouch(0).position);
}
}
if (_doubleTapTimer > 0.5f)
{
_doubleTapTimer = 0f;
_tapcount = 0;
}
Zoom = 0;
Rot = 0;
Pan = Vector3.zero;
Tilt = Vector3.zero;
if (_test == false)
{
FirstTouch = Vector2.zero;
SecondTouch = Vector3.zero;
ThirdTouch = Vector3.zero;
}
// Set Values for test
if (EnableTest)
{
if (Input.GetMouseButton(0) && Input.GetKey(KeyCode.LeftControl) && !Input.GetKey(KeyCode.LeftAlt))
{
FirstTouch = Input.mousePosition;
_test = true;
}
if (Input.GetMouseButton(0) && Input.GetKey(KeyCode.LeftAlt) && !Input.GetKey(KeyCode.LeftControl))
{
SecondTouch = Input.mousePosition;
_test = true;
}
if (Input.GetKey(KeyCode.LeftControl) && Input.GetKey(KeyCode.LeftAlt) && Input.GetMouseButton(0))
{
FirstTouch = Input.mousePosition;
SecondTouch = Input.mousePosition;
ThirdTouch = Input.mousePosition;
_test = true;
}
if (_test)
{
if (_firstbefore != Vector2.zero)
{
_firstdeltapos = FirstTouch - _firstbefore;
_seconddeltapos = SecondTouch - _secondbefore;
}
_firstbefore = FirstTouch;
_secondbefore = SecondTouch;
if (Input.GetKeyDown(KeyCode.Escape))
{
_test = false;
_firstdeltapos = Vector2.zero;
_seconddeltapos = Vector2.zero;
_firstbefore = Vector2.zero;
_secondbefore = Vector2.zero;
}
}
}
if (AllowTouchOverUI == false)
{
foreach (Touch touch in Input.touches)
{
int id = touch.fingerId;
if (EventSystem.current.IsPointerOverGameObject(id))
{
return;
}
}
}
// Set Values if no test
if (Input.touchCount == 1)
{
Touch First = Input.GetTouch(0);
FirstTouch = First.position;
_firstdeltapos = First.deltaPosition;
}
if (Input.touchCount == 2)
{
Touch First = Input.GetTouch(0);
Touch Second = Input.GetTouch(1);
FirstTouch = First.position;
_firstdeltapos = First.deltaPosition;
SecondTouch = Second.position;
_seconddeltapos = Second.deltaPosition;
}
if (Input.touchCount == 3)
{
Touch First = Input.GetTouch(0);
Touch Second = Input.GetTouch(1);
Touch Third = Input.GetTouch(2);
FirstTouch = First.position;
_firstdeltapos = First.deltaPosition;
SecondTouch = Second.position;
_seconddeltapos = Second.deltaPosition;
ThirdTouch = Third.position;
}
// Set actions
if (Input.touchCount == 1 || (_test && SecondTouch == Vector2.zero))
{
if (EnableOneFingerPan)
{
Pan = _firstdeltapos;
if (DebugLog)
Debug.Log("One Finger Touch Pan: " + Pan);
// Call Delegates
if (oneTouchPanEvent != null)
{
oneTouchPanEvent(FirstTouch, Pan);
}
}
}
if (Input.touchCount == 2 || (_test && SecondTouch != Vector2.zero && ThirdTouch == Vector2.zero))
{
// Find the position in the previous frame of each touch
var action = false;
Vector2 firstTouchPrevPos = FirstTouch - _firstdeltapos;
Vector2 secondTouchPrevPos = SecondTouch - _seconddeltapos;
float prevTouchDeltaMag = (firstTouchPrevPos - secondTouchPrevPos).magnitude;
float touchDeltaMag = (FirstTouch - SecondTouch).magnitude;
// Find the difference in the distances between each frame.
float deltaMagnitudeDiff = prevTouchDeltaMag - touchDeltaMag;
if (EnableZoom)
{
Zoom = -deltaMagnitudeDiff;
action = true;
}
// Pan
if (EnableTwoFingerPan)
{
Pan = _firstdeltapos;
action = true;
}
// Rotation
if (EnableRotation)
{
// Delta Degrees between vectors between two fingers
Vector2 vectorprevpos = firstTouchPrevPos - secondTouchPrevPos;
Vector2 vectorpos = FirstTouch - SecondTouch;
Rot = Vector2.SignedAngle(vectorpos, vectorprevpos);
if (Math.Abs(Rot) > MinRot)
{
action = true;
}
else
{
Rot = 0;
}
}
if (DebugLog)
Debug.Log("Two Finger Touch Pan: " + Pan + " Zoom: " + Zoom + " Rot: " + Rot);
// Call Delegates
if (twoTouchPanZoomRotDelegate != null && action)
{
var MidPos = FirstTouch + (SecondTouch - FirstTouch) / 2;
twoTouchPanZoomRotDelegate(MidPos, Pan, Zoom, Rot);
}
}
if (Input.touchCount == 3 || (_test && ThirdTouch != Vector2.zero && SecondTouch != Vector2.zero))
{
if (EnableTilt)
{
Tilt = _firstdeltapos;
if (DebugLog)
Debug.Log("Three Finger Tilt Touch: " + Tilt);
if (threeTouchPanDelegate != null)
{
var MidPos = FirstTouch + (ThirdTouch - FirstTouch) / 2;
threeTouchPanDelegate(MidPos, Tilt);
}
}
}
}
}
}