iOS响应事件传递, nextResponder研究
這里,我們考慮以下二種情況。
問題1。 如何調用父view的controller里面的方法?
答案如下:
[[self superview ].nextResponder??method];
[[[self superview ] nextResponder]??method];
[self.nextResponder method];
上面的都可以,看情況使用,使用的時候最好判斷一下。
官方解釋
UIView implements this method by returning the UIViewController object that manages it (if it has one) or its superview (if it doesn’t); UIViewController implements the method by returning its view’s superview; UIWindow returns the application object, and UIApplication returns nil.
即如下代碼可以進行判斷:
id?next = [self?nextResponder];
while(![next?isKindOfClass:[ViewController?class]])//這里跳不出來。。。有人說這里跳不出來,其實是因為它沒有當前這個view放入ViewController中,自然也就跳不出來了,會死循環,使用時需要注意。
{
next = [next?nextResponder];
}
if?([next?isKindOfClass:[ViewController?class]])
{
controller = (ViewController?*)next;
}
問題2:當一個子view需要接收點擊事件,而父view也需要接收點擊事件, 如何做?
當然, 你可能會說直接調用mysubview.superView即可, 這樣做也確實是可以做到,但有時子view是不一定知道有這個特定的父view的存在的,如動態添加子view。
所以這里就可以用到消息響應鏈拉技術。
下面要做的也就是,讓子view接收這些事件后,同時把這些事件繼續向上傳,會一直傳到UIApplication為止。 而在傳的過程中,如果子view接收了這些事件,那么事件會自然終止,我們現在可以做的是同時讓子view接收事件,而且還讓事件不終止,并繼續向上傳。
摘取一部分說明:
“當用戶 ?與 ?iPhone的觸摸屏 ?產生 ?互動時,硬件 ?就會探測到 ?物理接觸 ?并且 ?通知 ?操作系統。接著 ?操作系統 ?就會創建 ?相應的事件 ?并且 ?將 ?其 ?傳遞給 ?當前正在運行的應用程序的事件隊列。然后 ?這項事件 ?會被事件循環 ?傳遞給 ?優先響應者物件。優先響應者物件 ?是 ?事件 ?被觸發時 ?和 ?用戶 ?交互的物件,比如 ?按鈕物件、視圖物件。如果 ?我們 ?編寫了 ?代碼 ?讓 ?優先響應者 ?處理 ?這種類型的事件,那么 ?它 ?就會處理 ?這種類型的事件。處理完 ?某項事件后,響應者 ?有 ?兩個選項:1、將 ?其 ?丟棄;2、將 ?其 ?傳遞給 ?響應鏈條中的下一個響應者。下一個響應者的地址 ? 存儲 ?在當前響應者物件所包含的變量nextResponder當中。如果 ?優先響應者 ?無法處理 ?一項事件,那么 ?這項事件 ?就傳遞給 ?下一個響應者,直到 ?這項事件 ?到達 ?能處理它的響應者 ?或者 ?到達 ?響應鏈條的末端,也就是 ?UIApplication類型的物件。UIApplication類型的物件 ?收到 ?一項事件后,也是 ?要么 ?處理,要么 ?丟棄。“
比如 ?有 ?一個視圖物件,這個視圖物件上 ?有 ?一個按鈕物件。當用戶 ?觸摸 ?這個按鈕物件時,作為優先響應者,這個按鈕物件 ?就會收到 ?一項事件。如果 ?這個按鈕物件 ?無法處理 ?這項事件,就會將 ?這項事件 ?傳遞給 ?視圖物件。如果 ?視圖物件 ?無法處理 ?這項事件,就會將 ?這項事件 ?傳遞給 ?視圖控制器物件。以此類推。
應該注意的 ?是 ?當我們 ?在使用 ?響應鏈條時,一項事件 ?并不會自動地 ?從一個響應者 ?傳遞到 ?下一個響應者。如果 ?要將 ?一項事件 ?從一個響應者 ?傳遞到 ?下一個響應者,我們 ?必須編寫 ?代碼 ?才能辦到。”
要做的如下:
子view的代碼如下:
- (void)touchesBegan:(NSSet?*)touches withEvent:(UIEvent?*)event
{
// 這里可以做子view自己想做的事,做完后,事件繼續上傳,就可以讓其父類,甚至父viewcontroller獲取到這個事件了
[[selfnextResponder]touchesBegan:toucheswithEvent:event];
}
- (void)touchesEnded:(NSSet?*)touches withEvent:(UIEvent?*)event
{
[[selfnextResponder]touchesEnded:toucheswithEvent:event];
}
- (void)touchesCancelled:(NSSet?*)touches withEvent:(UIEvent?*)event
{
[[selfnextResponder]?touchesCancelled:toucheswithEvent:event];
}
- (void)touchesMoved:(NSSet?*)touches withEvent:(UIEvent?*)event
{
[[selfnextResponder]?touchesMoved:toucheswithEvent:event];
}
另外需要注意的是:在重寫這幾個方法時,最好保證這幾個方法都重寫,否則事件響應鏈可能會變混亂。這是我的猜測哈,沒有實際驗證過。總結
以上是生活随笔為你收集整理的iOS响应事件传递, nextResponder研究的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Xcode6的新特性、iPhone6和i
- 下一篇: ios 耳机线控