Dodgy Touch Controls / Performance Issues on iOS

If it isn’t one thing…

With a bit of help from some other Unity Answers members, I managed to get my iOS program up to the point where it can detect flick inputs (as well as direction) and Instantiate game objects at touch. It can even distinguish between the two inputs.

The problem is that it often makes mistakes. I know that some performance issues are to be expected when using Unity Remote but even when run directly off our iPhone 3G - it misreads inputs, converts some swipes into taps, or completely reads a swipe backwards.

Just looking at my code, is there something I’m doing wrong? I mean, it works so doesn’t that mean that the code is correct? How am I supposed to compensate for the hardware?

Anway, if you could take a look at what I have and tell me if I’m doing something wrong (or any other red flags) I’d really appreciate it.

Thanks.

using UnityEngine;
using System.Collections;

public class Flick : MonoBehaviour {

//public GameObject attractorPrefab;	
public GameObject exploderPrefab;
public GameObject petal;
	
public float coolDown;
public float speed;
public float startTime;
public float swipeTime;
public float comfortZone;
public float minSwipeDistance;
public float maxSwipeTime;
public float swipeThresh;		
	   float swipeSpeed;
	   float inputX;
	   float inputY;	

public int count;
public int tapCount;
	
public bool couldBeSwipe;
public bool swipeWasActive;
public bool gotStartPoint;
public bool gotEndPoint;	
public bool inFlight;
	
public Vector2 startPosition;
public Vector2 endPosition;
	   Vector2 swipeStart;
	   Vector2 swipeEnd;
	
public Vector3 hp;
public Vector3 hitPointA;
public Vector3 hitPointB;
public Vector3 changeCoordinates;
	  
	   Touch touch;
		
	void Start () 
    {
		speed = 3.0f; 			//speed for wind stream
		swipeThresh = 0.5f; 	//swipe sensitivity
		
		gotStartPoint = false;
		gotEndPoint = false;
		swipeWasActive = false;
				
		petal = GameObject.Find("petal");
		
		coolDown = 0; 			//input delay counter
		inFlight = false; 		//check to see if petal is in wind stream or not
    }

    void Update () 
    {
		coolDown -= Time.deltaTime;
		
		if (coolDown < 0)
			coolDown = 0;
		if(((Input.touchCount == 1) && (Input.GetTouch(0).phase == TouchPhase.Moved)) && (coolDown == 0))
		{
			processSwipe();
		}
		else
		if(((Input.touchCount == 1) && (Input.GetTouch(0).phase == TouchPhase.Ended)) && ((coolDown == 0) && (inFlight == false)))
		{
			Debug.Log("Instantiate explosion");
					
				
			//touchPosition = new Vector3(touchPosition.x, touchPosition.y, 0);
			Ray ray = camera.ScreenPointToRay(new Vector3(Input.GetTouch(0).position.x, Input.GetTouch(0).position.y, 0));
			//Input.GetTouch(0).position.z = 10;
			RaycastHit hit;
						
			if(Physics.Raycast(ray, out hit))
			{
				Vector3 hp = hit.point;
				hp.z = 0;
					
				//Create explosion
				Instantiate (exploderPrefab, hp, Quaternion.identity);
				coolDown = 0.5f;
			}
		}else
		if(((Input.touchCount == 1) && (inFlight == true)) && (Input.GetTouch(0).phase == TouchPhase.Began))
		{
			Reset();
		}
		
		if((gotStartPoint == true) && (gotEndPoint == true))
		{
			petal.rigidbody.useGravity = false;
			petal.transform.Translate(changeCoordinates.normalized * (Time.deltaTime * speed), Space.World);
			inFlight = true;
			Debug.Log("touchCount: "+Input.touchCount);
		}
	}
	
	void processSwipe()
	{
		if (Input.touchCount != 1)
		{
			return;
		}
		
		Touch theTouch = Input.touches[0];
		
		//Skip the frame if deltaPosition is zero.
		
		if (theTouch.deltaPosition == Vector2.zero)
		{
			return;
		}
		
		Vector2 speedVec = theTouch.deltaPosition * theTouch.deltaTime;
		float theSpeed = speedVec.magnitude;
		
		bool swipeIsActive;
		swipeIsActive = (theSpeed > swipeThresh);
		
		if (swipeIsActive)
		{
			if(!swipeWasActive)
			{
				swipeStart = theTouch.position;
				Ray ray = camera.ScreenPointToRay(swipeStart);
				RaycastHit hit;
				
				if (Physics.Raycast(ray, out hit))
				{
					hitPointA = hit.point;
					hitPointA.z = 0;
					Debug.Log("Hit Point A: "+hitPointA);
				}
				Debug.Log("Swipe start pos: "+swipeStart);
				
				gotStartPoint = true;
				Debug.Log("gotStartPoint =  true!");
			}
		}
		
		else
		{
			if(swipeWasActive)
			{
				swipeEnd = theTouch.position;
				Ray ray =  camera.ScreenPointToRay(swipeEnd);
				RaycastHit hit;
				
				if(Physics.Raycast(ray, out hit))
				{
					hitPointB = hit.point;
					hitPointB.z = 0;
					Debug.Log("Hit Point B: "+hitPointB);
				}
				Debug.Log("Swipe end pos: "+swipeEnd);
				gotEndPoint = true;
				Debug.Log("gotEndPoint = true!");
				
				changeCoordinates = (hitPointB - hitPointA);
				Debug.Log("Change Coordinates: "+changeCoordinates);
			}
		}
		
		swipeWasActive = swipeIsActive;
	}
	
	void Reset()
	{
		Debug.Log("Reset!");
		
		inFlight = false;
		gotStartPoint = false;
		gotEndPoint = false;
		
		petal.rigidbody.useGravity = true;
		
		coolDown = 0.5f;
	}
}

Will close this question as I managed to figure out a passable solution. Needed to construct a system based around bools to determine whether a key was in a “pressed” state and then to check if there was actual input on the device.

Was a pain the butt, but happy with the results.