UIView子类没有收到touchesBegan,touchesEnded [英] UIView subclass not receiving touchesBegan, touchesEnded
问题描述
好吧,所以我有一个应用程序的子类UIView,并依靠touchesBegan和touchesEnded。我指的是这些回调:
Ok- so I have an application which subclasses UIView, and relies on touchesBegan and touchesEnded. I refer of course to these callbacks:
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
我更新我的iOS从7到9只是在另一天(我知道,我很懒惰)发现触摸不工作。原来以上的功能没有得到调用在我的UIView子类。好奇,我开始一个空白的项目,这是足够短,我只是发布代码在这里。
I updated my iOS from 7 to 9 just the other day (I know, I'm lazy) to find that the touches aren't working. Turns out the above functions aren't getting called in my UIView subclass. Curious, I started a blank project, which is short enough that I'll just post the code here.
main.m:
#import <UIKit/UIKit.h>
#import "AppDelegate.h"
int main(int argc, char * argv[]) {
@autoreleasepool {
return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));
}
}
这里是AppDelegate。动态创建窗口和视图。
Here's AppDelegate. Create a window and a view dynamically.
#import "AppDelegate.h"
#import "SubView.h"
@implementation AppDelegate
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
//create a window and give it a frame. makeKeyAndVisible
CGRect rect = [[UIScreen mainScreen] bounds];
self.window = [[UIWindow alloc] initWithFrame:rect];
self.window.frame = [[UIScreen mainScreen] bounds];
[self.window makeKeyAndVisible];
//Create a subview. Make it a red square. make sure it has a background.
//set the userInteractionEnabled and multipleTouchEnabled and for
//good meausure call becomeFirstResponder.
SubView *view = [[SubView alloc] initWithFrame:CGRectMake(100,100,100,100)];
view.backgroundColor = [UIColor redColor];
[self.window addSubview:view];
view.userInteractionEnabled = YES;
view.multipleTouchEnabled = YES;
[view becomeFirstResponder];
//Create default UIViewControllers because Objective-C fails if the windows don't have
//root view controllers. I don't like being muscled into MVC but what are you gonna do
NSArray *windows = [[UIApplication sharedApplication] windows];
for(UIWindow *window in windows) {
if(window.rootViewController == nil){
UIViewController* vc = [[UIViewController alloc]initWithNibName:nil bundle:nil];
window.rootViewController = vc;
window.userInteractionEnabled = YES;
window.multipleTouchEnabled = YES;
}
}
return YES;
}
@end
这里是SubView类。只是有touchesBegan touchesEnded。
And here's the SubView class. Does just has the touchesBegan touchesEnded.
SubView.h
SubView.h
#import <Foundation/Foundation.h>
#import <UIKit/UIKit.h>
@interface SubView : UIView {
}
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event;
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event;
@end
SubView.m
SubView.m
#import "SubView.h"
@implementation SubView
//delegate method for touches began
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
//[super touchesBegan:touches withEvent:event];
NSLog(@"touchesBegan!");
}
//delegate method for touches ending.
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
//[super touchesEnded:touches withEvent:event];
NSLog(@"touchesEnded!");
}
//just for good measure.
- (BOOL) canBecomeFirstResponder {
return YES;
}
@end
很简单。创建一个窗口,创建一个SubView,添加SubView到窗口,设置userInteractionEnabled。然而,它不工作。我看过下面的S.O.帖子:
Pretty simple. Create a window, create a SubView, add SubView to the window, set userInteractionEnabled. And yet, it doesn't work. I've looked at the following S.O. posts:
iPhone SDK - 将触摸从UIViewController转发到子视图
touchesBegan in UIView not being called
他们都说userInteractionEnabled = YES应该修复它,或者可能有视图覆盖另一个视图,或者视图可能有一个透明的背景。这里没有适用。我设置了view.userInteractionEnabled = YES,我甚至试图给视图第一响应者状态。没有一个似乎做任何好处。
They all say userInteractionEnabled = YES should fix it, or there might be view covering another view, or the view might have a transparent background. None of that applies here. I've set view.userInteractionEnabled = YES, and I've even tried to give the view first-responder status. None of it seems to do any good.
精明观察者也会看到我在窗口本身设置这些值:
Astute observers will also see that I'm setting these values on the window itself:
window.userInteractionEnabled = YES;
window.multipleTouchEnabled = YES;
我试过了。没有骰子。我试过调用
I've tried it with and without. No dice. I've tried calling
[super touchesBegan:touches withEvent:event]
和
[super touchesEnded:touches withEvent:event]
。没有骰子。任何帮助,你可以给我将非常感谢。感谢!
in those callbacks on SubView. No dice. Any help you can give me would be greatly appreciated. Thanks!
推荐答案
在应用程序运行时查看您的视图层次结构,可以使用 recursiveDescription
或使用Xcode 7的Debug View Hierarchy按钮。
Look at your view hierarchy while the app is running, either using recursiveDescription
or using Xcode 7's "Debug View Hierarchy" button.
(lldb) po [[[UIApplication sharedApplication] keyWindow] recursiveDescription]
<UIWindow: 0x7fc1f9d17b20; frame = (0 0; 414 736); gestureRecognizers = <NSArray: 0x7fc1f9d18910>; layer = <UIWindowLayer: 0x7fc1f9d16560>>
| <SubView: 0x7fc1f9c04350; frame = (100 100; 100 100); layer = <CALayer: 0x7fc1f9c04730>>
| <UIView: 0x7fc1f9c07500; frame = (0 0; 414 736); autoresize = W+H; layer = <CALayer: 0x7fc1f9c07fc0>>
稍后在子视图列表中的视图更接近屏幕,因此首先接收触摸。由通用 UIViewController
创建的视图填充窗口,位于 SubView
前面。因此您的 SubView
无法接收触摸。
Views later in the list of subviews are "closer" to the screen and thus receives touches first. The view created by the generic UIViewController
fills the window and is in front of your SubView
. Thus your SubView
can't receive touches.
Apple添加了 rootViewController
属性到 UIWindow
在iOS 4.0 - 五年前。通过战斗,你只是为自己做麻烦。只需让 rootViewController.view
成为窗口中的单个顶级视图,并在其下添加子视图。没有人强迫您向您的应用添加任何其他视图控制器。
Apple added the rootViewController
property to UIWindow
in iOS 4.0—over five years ago. By fighting it, you're only making trouble for yourself. Just let rootViewController.view
be the single top-level view in your window, and add your subviews under that. Nobody's forcing you to add any other view controllers to your app.
这篇关于UIView子类没有收到touchesBegan,touchesEnded的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!