void Update(){// ON PC UPDATE MUST BE COMMENTED OUT
if (Input.GetTouch(0).phase == TouchPhase.Began) {
ray = _main.ScreenPointToRay(Input.GetTouch(0).position);
if (Physics.Raycast(ray, out hit, 100,1<<gameObject.layer)){//hit on the very same object
TouchDown();
}
}else if (Input.GetTouch(0).phase == TouchPhase.Ended||Input.GetTouch(0).phase == TouchPhase.Canceled) {
TouchUp();
}
}
When deployed to Android everything works as expected, but when I release a finger than quickly tap on another location TouchUp doesnât get called like the old finger is still acting though I was expecting TouchUp would fire uo and another Touch sequence begins with index 0, now I donât know what speed at Ended would be missed at but is it that I maybe tapped another finger at less than 30ms or so between taps that Update couldnât keep track of the new tap and Unity took it fo the old one?
I tried to use fingerId but I donât quite get how they work nor how unity indexes touches, the docs say just:
Touch.fingerId
var fingerId: int;
Description
The unique index for touch.
No potential values no example no rule of thub, WTF?
Every time a new touch happens, the touch object gets a unique index. I donât know exactly what these indices look like, but perhaps itâs just an incrementing number. This means that you can track touch objects and donât need to rely on the position in the array. So, the documentation is pretty good. Each touch gets a unique index. Maybe Debug.Log the index and youâll quickly get the idea.
You could keep a track of the touch index. If the ânewâ touch index differs from the last touch index, then you have a new touch, and possibly the Ended has been missed (but I doubt it, see below.)
You really should assume that youâll get multiple touches. In one frame you might have a new touch event starting and an old one ending. This could mean you have 2 TouchEvents even though you only have a single finger down. So, use Input.touchCount, as the last two examples on the GetTouch page show.
Sorry for the thread necro, but I just ran into the head-line bug when testing touch on WebGL in Safari on an iPad Air 3.
After considerable testing I can verify that when multi-touch has one Moving touch, the other touch will frequently fail to report an Ended or Canceled phase. (e.g. left touch = movement/strafing, right touch = turning).
My solution is to store the fingerId for both the move and the turn when they are âBeganâ. If we get any phase except Canceled/Ended then set a boolean true for that input.
After processing all touches, check the bools, if either is false, call the TouchEnd method for that id.
bool moveInput = false, turnInput = false;
for (int i = 0, l = Input.touchCount; i < l; i++)
{
Touch t = Input.GetTouch(i);
Debug.Log($"touch {i} {t.phase}");
switch (t.phase)
{
case TouchPhase.Began:
TouchStart(t);
break;
case TouchPhase.Moved:
TouchMove(t);
break;
//case TouchPhase.Canceled:
//case TouchPhase.Ended:
// TouchEnd(t.fingerId);
// break;
}
if (t.phase != TouchPhase.Ended && t.phase != TouchPhase.Canceled)
{
if (t.fingerId == moveId) moveInput = true;
if (t.fingerId == turnId) turnInput = true;
}
}
if (moveInput == false && moveId != -1)
{
TouchEnd(moveId);
moveId = -1;
}
if (turnInput == false && turnId != -1)
{
TouchEnd(turnId);
turnId = -1;
}