From 224bd05b4c5688f1bca0b3fa96b62165cfa221b0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Rydg=C3=A5rd?= Date: Sat, 20 Feb 2021 13:09:54 +0100 Subject: [PATCH] iOS: Fix multitouch tracking. Patterned on #9602. Fixes #5099. Note that the iPhone supports max 5 touches and will cancel all on the 6th touch. That's platform behavior that can't be changed. We interpret touch cancellation as touch up. --- ios/PPSSPP-Info.plist | 2 +- ios/ViewController.mm | 70 +++++++++++++++++++++++-------------------- 2 files changed, 39 insertions(+), 33 deletions(-) diff --git a/ios/PPSSPP-Info.plist b/ios/PPSSPP-Info.plist index 55d219357c..66d14406c8 100644 --- a/ios/PPSSPP-Info.plist +++ b/ios/PPSSPP-Info.plist @@ -17,7 +17,7 @@ CFBundleExecutable PPSSPP CFBundleIdentifier - org.ppsspp.ppsspp + org.ppsspp.ppsspptest CFBundleInfoDictionaryVersion 6.0 CFBundleName diff --git a/ios/ViewController.mm b/ios/ViewController.mm index 59bd731ee4..5d810ad3b4 100644 --- a/ios/ViewController.mm +++ b/ios/ViewController.mm @@ -96,6 +96,7 @@ static double lastStartPress = 0.0f; static bool simulateAnalog = false; static bool threadEnabled = true; static bool threadStopped = false; +static UITouch *g_touches[10]; __unsafe_unretained ViewController* sharedViewController; static GraphicsContext *graphicsContext; @@ -107,7 +108,7 @@ static LocationHelper *locationHelper; } @property (nonatomic, strong) EAGLContext* context; -@property (nonatomic, strong) NSMutableArray* touches; + //@property (nonatomic) iCadeReaderView* iCadeView; #if __IPHONE_OS_VERSION_MAX_ALLOWED > __IPHONE_6_1 @property (nonatomic) GCController *gameController __attribute__((weak_import)); @@ -127,7 +128,7 @@ static LocationHelper *locationHelper; self = [super init]; if (self) { sharedViewController = self; - self.touches = [NSMutableArray array]; + memset(g_touches, 0, sizeof(g_touches)); iCadeToKeyMap[iCadeJoystickUp] = NKCODE_DPAD_UP; iCadeToKeyMap[iCadeJoystickRight] = NKCODE_DPAD_RIGHT; @@ -384,37 +385,38 @@ static LocationHelper *locationHelper; NativeTouch(input); } -- (NSDictionary*)touchDictBy:(UITouch*)touch -{ - for (NSDictionary* dict in self.touches) { - if ([dict objectForKey:@"touch"] == touch) - return dict; - } - return nil; -} - -- (int)freeTouchIndex -{ - int index = 0; - - for (NSDictionary* dict in self.touches) - { - int i = [[dict objectForKey:@"index"] intValue]; - if (index == i) - index = i+1; +int ToTouchID(UITouch *uiTouch, bool allowAllocate) { + // Find the id for the touch. Avoid 0 (mouse.) + for (int localId = 1; localId < (int)ARRAY_SIZE(g_touches); ++localId) { + if (g_touches[localId] == uiTouch) { + return localId; + } } - return index; + // Allocate a new one, perhaps? + if (allowAllocate) { + for (int localId = 1; localId < (int)ARRAY_SIZE(g_touches); ++localId) { + if (g_touches[localId] == 0) { + g_touches[localId] = uiTouch; + return localId; + } + } + + // None were free. Ignore? + return 0; + } + + return -1; } + - (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event { for(UITouch* touch in touches) { - NSDictionary* dict = @{@"touch":touch,@"index":@([self freeTouchIndex])}; - [self.touches addObject:dict]; CGPoint point = [touch locationInView:self.view]; - [self touchX:point.x y:point.y code:1 pointerId:[[dict objectForKey:@"index"] intValue]]; + int touchId = ToTouchID(touch, true); + [self touchX:point.x y:point.y code:1 pointerId:touchId]; } } @@ -423,8 +425,8 @@ static LocationHelper *locationHelper; for(UITouch* touch in touches) { CGPoint point = [touch locationInView:self.view]; - NSDictionary* dict = [self touchDictBy:touch]; - [self touchX:point.x y:point.y code:0 pointerId:[[dict objectForKey:@"index"] intValue]]; + int touchId = ToTouchID(touch, true); + [self touchX:point.x y:point.y code:0 pointerId: touchId]; } } @@ -433,9 +435,11 @@ static LocationHelper *locationHelper; for(UITouch* touch in touches) { CGPoint point = [touch locationInView:self.view]; - NSDictionary* dict = [self touchDictBy:touch]; - [self touchX:point.x y:point.y code:2 pointerId:[[dict objectForKey:@"index"] intValue]]; - [self.touches removeObject:dict]; + int touchId = ToTouchID(touch, false); + if (touchId >= 0) { + [self touchX:point.x y:point.y code:2 pointerId: touchId]; + g_touches[touchId] = nullptr; + } } } @@ -444,9 +448,11 @@ static LocationHelper *locationHelper; for(UITouch* touch in touches) { CGPoint point = [touch locationInView:self.view]; - NSDictionary* dict = [self touchDictBy:touch]; - [self touchX:point.x y:point.y code:2 pointerId:[[dict objectForKey:@"index"] intValue]]; - [self.touches removeObject:dict]; + int touchId = ToTouchID(touch, false); + if (touchId >= 0) { + [self touchX:point.x y:point.y code:2 pointerId: touchId]; + g_touches[touchId] = nullptr; + } } }