亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 學院 > 開發設計 > 正文

iOSProgrammingTouchEventsandUIResponder

2019-11-14 19:03:16
字體:
來源:轉載
供稿:網友

iOS PRogramming Touch Events and UIResponder?

1 Touch Events?

As a subclass of UIResponder, a UIView can override four methods to handle the four distinct touch events:

作為UIResponder的一個子類,UIView可以重寫四個方法來處理touch events。

(1)

a finger or fingers touches the screen 開始觸摸
- (void)touchesBegan:(NSSet *)touches

withEvent:(UIEvent *)event;

(2)a finger or fingers moves across the screen (this message is sent repeatedly as a finger moves)滑動

- (void)touchesMoved:(NSSet *)touches

withEvent:(UIEvent *)event;

(3)a finger or fingers is removed from the screen 從屏幕上移除

- (void)touchesEnded:(NSSet *)touches

withEvent:(UIEvent *)event;

(4)a system event, like an incoming phone call, interrupts a touch before it ends 系統事件,比如一個電話進來,在它ends 之前打斷了touch .?

- (void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent *)event;

?

When a finger touches the screen, an instance of UITouch is created.

當手指觸摸屏幕時,一個UITouch 的實例就被創建了。?

The UIView that this finger touched? is sent the message touchesBegan:withEvent: and the UITouch is in the NSSet of touches.

手指觸摸的UIView 就會被發送消息touchesBegan:withEvent。并且UITouch 是一系列的觸摸集合。

?

As that finger moves around the screen, the touch object is updated to contain the current location of the finger on the screen.

當手指在屏幕上移動時,touch object就會被更新 來保鮮現在手指的位置。

Then, the same UIView that the touch began on is sent the message touchesMoved:withEvent:.

相同的UIView 就會被發送touchesMoved:withEvent。

The NSSet that is passed as an argument to this method contains the same UITouch that originally was created when the finger it represents touched the screen.

被傳遞參數的NSSet 包含 相同的UITouch。

?

When a finger is removed from the screen, the touch object is updated one last time to contain the current location of the finger, and the view that the touch began on is sent the message touchesEnded:withEvent:. After that method finishes executing, the UITouch object is destroyed.

當手指從屏幕上移走時,也會更新touch object 。會發送給UIView,touchesEnded:withEvent。在這個方法完成后,UITouch就會被銷毀。

?

(1)One UITouch corresponds to one finger on the screen. This touch object lives as long as the finger is on the screen and always contains the current position of the finger on the screen.

(2)The view that the finger started on will receive every touch event message for that finger no matter what. If the finger moves outside of the UIView's frame that it began on, that view still receives the touchesMoved:withEvent: and touchesEnded:withEvent: messages. Thus, if a touch begins on a view, then that view owns the touch for the life of the touch.

所以如果一個touch 從一個view 開始,那么這個view 擁有這個touch 的這個生命周期。

(3) You do not have to – nor should you ever – keep a reference to a UITouch object. The application will give you access to a touch object when it changes state.

你不需要,也不應該有一個引用對UITouch。 當它的狀態改變時,application將會給你它的獲取。

Every time a touch does something, like begins, moves, or ends, a touch event is added to a queue of events that the UIApplication object manages.

一個事件被添加到被UIApplication管理的一個事件隊列中。

In practice, the queue rarely fills up, and events are delivered immediately. The delivery of these touch events involves sending one of the UIResponder messages to the view that owns the touch.

touch event的傳遞包括發送一個UIResponder消息到擁有touch 的view。

?

What about multiple touches? If multiple fingers do the same thing at the exact same time to the same view, all of these touch events are delivered at once. Each touch object – one for each finger – is included in the NSSet passed as an argument in the UIResponder messages.

如何處理多點觸摸?

如果是多個手指做相同的事情在相同的時間,所有的這些觸摸事件就會一次被傳遞。每一個touch object ,每一個finger,包含在一個NSSet 中,作為UIResponder消息的一個參數。?

However, the window of opportunity for the "exact same time" is fairly short. So, instead of one responder message with all of the touches, there are usually multiple responder messages with one or more of the touches.

因為相同時間太少了,因此取而代之的事,多個responder 消息有一個或多個touches。

2Creating the TouchTracker Application

? let's get started with your application. In Xcode, create a new Empty Application iPhone project and

name it TouchTracker.

?

#import <Foundation/Foundation.h> @interface BNRLine : NSObject

@property (nonatomic) CGPoint begin; @property (nonatomic) CGPoint end;

@end

?

Next, create a new NSObject subclass called BNRDrawView. In BNRDrawView.h, change the superclass to UIView.

@interface BNRDrawView : UIView @end

@interface LKLine : NSObject

@property(nonatomic)CGPoint begin;

@property(nonatomic)CGPoint end;

@end

?

@interface LKDrawView : UIView

?

@end

?

-(void)loadView{

? ? self.view=[[LKDrawView alloc] initWithFrame:CGRectZero];

?? ??

}

?LKDrawViewController *drawViewController=[[LKDrawViewController alloc] init];

self.window.rootViewController=drawViewController;

?

3. Drawing with BNRDrawView

?

#import "BNRDrawView.h" #import "BNRLine.h"

@interface BNRDrawView ()

@property (nonatomic, strong) BNRLine *currentLine; @property (nonatomic, strong) NSMutableArray *finishedLines;

@end

?

- (instancetype)initWithFrame:(CGRect)r

{
self = [super initWithFrame:r];

if (self) {
self.finishedLines = [[NSMutableArray alloc] init];

self.backgroundColor = [UIColor grayColor]; }

return self; }

?

- (void)strokeLine:(BNRLine *)line

{
UIBezierPath *bp = [UIBezierPath bezierPath]; bp.lineWidth = 10;
bp.lineCapStyle = kCGLineCapRound;

[bp moveToPoint:line.begin]; [bp addLineToPoint:line.end]; [bp stroke];

}

?

- (void)drawRect:(CGRect)rect

{
// Draw finished lines in black
[[UIColor blackColor] set];
for (BNRLine *line in self.finishedLines) {

[self strokeLine:line]; }

if (self.currentLine) {
// If there is a line currently being drawn, do it in red [[UIColor redColor] set];
[self strokeLine:self.currentLine];

} }

?

4 Turning Touches into Lines

A line is defined by two points. Your BNRLine stores these points as properties named begin and end.

?

When a touch begins, you will create a line and set both begin and end to the point where the touch began. When the touch moves, you will update end. When the touch ends, you will have your complete line.

當觸摸開始時,就設置begin和end 屬性,當移動時,就更新end 。當touch 結束,就完成了line。?

?

-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{

? ? UITouch *touch=[touches anyObject];

? ? CGPoint location=[touch locationInView:self];

? ? self.currentLine=[[LKLine alloc]init];

? ? self.currentLine.begin=location;

? ? self.currentLine.end=location;

?? ??

? ? [self setNeedsDisplay];

}

-(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{

? ? UITouch *touch=[touches anyObject];

? ? CGPoint location=[touch locationInView:self];

? ? self.currentLine.end=location;

? ? [self setNeedsDisplay];

?? ??

}

?

-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event{

? ? [self.finishedLines addObject:self.currentLine];

? ? self.currentLine=nil;

? ? [self setNeedsDisplay];

}

?

5 ?Handling multiple touches

By default, a view will only accept one touch at a time.

默認情況下,view 只能在同一時刻接受一個touch。

If one finger has already triggered touchesBegan:withEvent: but has not finished – and therefore has not triggered touchesEnded:withEvent: – subsequent touches are ignored.

如果一個手指已經觸發了touchesBegan:withEvent,但是還沒有結束,因此沒有觸發touchesEnded:withEvent:, 它的子序列touch 將會被忽略。

In this context, "ignore" means that the BNRDrawView will not be sent touchesBegan:withEvent: or any other UIResponder messages related to the extra touches.

ignore的意思是BNRDrawView將不會被送touchesBegan:withEvent或者任何其他的與多余的touches相關的UIResponder消息?

?

In BNRDrawView.m, enable BNRDrawView instances to accept multiple touches.

????????self.multipleTouchEnabled=YES;

Now that BNRDrawView will accept multiple touches, each time a finger touches the screen, moves, or is removed from the screen, the view will receive the appropriate UIResponder message.

這個時候就可以接受對應的UIResponder消息了。

However, this now presents a problem: your UIResponder code assumes there will only be one touch active and one line being drawn at a time.

你的UIResponder code 假設只有一個touch active 并且在同一時間只能畫一條線。

?

Notice, first, that each touch handling method you have already implemented sends the message anyObject to the NSSet of touches it receives.

In a single-touch view, there will only ever be one object in the set, so asking for any object will always give you the touch that triggered the event.

在single-touch view, 在一個set 中只有一個對象,所以要求任意對象將會觸發事件。

?

In a multiple touch view, that set could contain more than one touch.

在multiple touch view,set 可能含有多個touch。?

?

While you could create a few more properties, like currentLine1 and currentLine2, you would have to go to considerable lengths to manage which instance variable corresponds to which touch.

?

Instead of the multiple property approach, you can use an NSMutableDictionary to hang on to each BNRLine in progress.

?你可以用字典來代表在程序中得line。?

The key to store the line in the dictionary will be derived from the UITouch object that the line corresponds to.

存儲line 在字典中的關鍵字將會從 這個line 對應的UITouch 對象中獲取。?

As more touch events occur, you can use the same algorithm to derive the key from the UITouch that triggered the event and use it to look up the appropriate BNRLine in the dictionary.

?

notice the use of valueWithNonretainedObject: to derive the key to store the BNRLine.

This method creates an NSValue instance that holds on to the address of the UITouch object that will be associated with this line.

這個方法創建了一個NSValue 實例,來保持這個UITouch對象的地址。

?Since a UITouch is created when a touch begins, updated throughout its lifetime, and destroyed when the touch ends, the address of that object will be constant through each touch event message.

因為一個UITouch 在touch開始創建,在生命周期更新,在touch end 銷毀,因此這個對象的地址在整個touch event 是個常量。

?for (UITouch *touch in touches) {

? ? ? ? CGPoint location=[touch locationInView:self];

? ? ? ? LKLine *line=[[LKLine alloc]init];

? ? ? ? line.begin=location;

? ? ? ? line.end=location;

? ? ? ? NSValue *key=[NSValue valueWithNonretainedObject:touch];

? ? ? ? self.linesInProgress[key]=line;

?? ? ? ??

? ? }

?

?

why not use the UITouch itself as the key? Why go through the hoop of creating an NSValue? Objects used as keys in an NSDictionary must conform to the NSCopying protocol, which allows them to be copied by sending the message copy. UITouch instances do not conform to this protocol because it does not make sense for them to be copied. Thus, the NSValue instances hold the address of the UITouch so that equal NSValue instances can be later created with the same UITouch.

?

?

The last thing left for the basics of TouchTracker is to handle what happens when a touch is cancelled.

最后一件事當觸摸被取消如何處理

A touch can be cancelled when an application is interrupted by the Operating system (for example, a phone call comes in) when a touch is currently on the screen.

When a touch is cancelled, any state it set up should be reverted.

如果一個touch 被取消,它的任何設置狀態應該被取消。

-(void)touchesCancelled:(NSSet?*)touches withEvent:(UIEvent?*)event{
???
?NSLog(@"%@",NSStringFromSelector(_cmd));
???
?for?(UITouch?*touch?in?touches) {
???????
?NSValue?*key=[NSValue?valueWithNonretainedObject:touch];
??????? [self.linesInProgress
?removeObjectForKey:key];
??? }
??? [self
?setNeedsDisplay];

}

?

?

?

?

?


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
亚洲的天堂在线中文字幕| 国内偷自视频区视频综合| 久久精品99久久久香蕉| 中文字幕在线国产精品| 91精品综合视频| 国产精品一区二区av影院萌芽| 亚洲成人av在线| 欧美激情成人在线视频| 91精品国产91久久久久久久久| 日韩欧美中文免费| 国产成人精品综合久久久| 亚洲丝袜av一区| 国产精品福利网| 午夜精品视频在线| 91在线观看免费高清| 亚洲免费一在线| 日本精品久久久| 欧美激情二区三区| 午夜精品一区二区三区在线视频| 亚洲欧洲午夜一线一品| 久久久女人电视剧免费播放下载| 亚洲a成v人在线观看| 一个色综合导航| 91高潮在线观看| 日本亚洲欧美成人| 美女视频久久黄| 欧美日韩成人黄色| 4438全国亚洲精品在线观看视频| 国产一区二中文字幕在线看| 91久久久久久久久久久久久| 欧美国产第一页| 久久久久久com| 午夜精品一区二区三区在线视| 日韩中文字幕在线| 在线播放国产一区二区三区| 中文字幕精品www乱入免费视频| 日韩一区二区久久久| 亚洲欧洲xxxx| 精品久久久一区二区| 亚洲精品久久视频| 色偷偷噜噜噜亚洲男人| 久久人人爽亚洲精品天堂| 欧美人与性动交a欧美精品| 97精品免费视频| 97视频免费在线看| 日韩在线播放一区| 亚洲成人免费网站| 综合网日日天干夜夜久久| 午夜美女久久久久爽久久| 91伊人影院在线播放| 国产香蕉精品视频一区二区三区| 黑人巨大精品欧美一区二区三区| 国产一区二区成人| 国产精品av在线| 国产成人精品久久久| 欧美在线视频免费观看| 亚洲香蕉伊综合在人在线视看| 亚洲色图综合网| 欧美性猛交xxxx乱大交3| 97视频免费看| 亚洲视屏在线播放| 久久久久99精品久久久久| 国产一区二区在线播放| 亚洲激情在线视频| 亚洲一区二区三区毛片| 日韩精品在线免费| 91福利视频网| 日韩一二三在线视频播| 国产精品三级在线| 国产在线98福利播放视频| 4k岛国日韩精品**专区| 国产91在线播放| 91久久精品日日躁夜夜躁国产| 亚洲欧洲自拍偷拍| 日韩一区二区在线视频| 欧美美最猛性xxxxxx| 国产精品v日韩精品| 国产精品一区二区久久精品| 日韩在线国产精品| 精品视频久久久久久| 亚洲3p在线观看| 欧美另类精品xxxx孕妇| 国产精品69精品一区二区三区| 97国产一区二区精品久久呦| 日韩成人av在线| 色www亚洲国产张柏芝| 久久久精品中文字幕| 爱福利视频一区| 成人黄色影片在线| 亚洲精品一区av在线播放| 成人美女av在线直播| 庆余年2免费日韩剧观看大牛| 美日韩精品免费视频| 日韩av最新在线| 红桃视频成人在线观看| 不卡在线观看电视剧完整版| 日韩性xxxx爱| 91精品视频在线播放| 成人伊人精品色xxxx视频| 91久久嫩草影院一区二区| 亚洲第一网站男人都懂| 国产97色在线|日韩| 国产精品夫妻激情| 一本一道久久a久久精品逆3p| 国产精品成久久久久三级| 久久视频这里只有精品| 久久影院免费观看| 91欧美精品午夜性色福利在线| 欧美视频一二三| 欧美电影免费观看电视剧大全| 久久视频中文字幕| 国内成人精品一区| 亚洲电影免费观看高清完整版| 久久影院资源网| 6080yy精品一区二区三区| 久久精品国亚洲| 亚洲福利视频在线| 精品国内亚洲在观看18黄| 91极品女神在线| 超碰97人人做人人爱少妇| 蜜月aⅴ免费一区二区三区| 亚洲а∨天堂久久精品喷水| 91在线播放国产| 精品露脸国产偷人在视频| 日韩免费在线免费观看| 国产丝袜一区视频在线观看| 亚洲成人性视频| 黑人巨大精品欧美一区二区一视频| 日韩精品在线电影| 98午夜经典影视| 韩国v欧美v日本v亚洲| 国产一区二区三区四区福利| 97免费视频在线| 欧美在线中文字幕| 中文字幕自拍vr一区二区三区| 8090理伦午夜在线电影| 亚洲一区美女视频在线观看免费| 国产免费一区二区三区在线观看| 欧美一级淫片丝袜脚交| 在线精品视频视频中文字幕| 国产精品香蕉在线观看| 中文字幕日韩精品在线| 精品国产一区二区三区久久久| 日韩av中文字幕在线| 日日噜噜噜夜夜爽亚洲精品| 中文字幕av一区二区三区谷原希美| 精品一区电影国产| 亚洲欧洲成视频免费观看| 亚洲欧美国内爽妇网| 国产大片精品免费永久看nba| 国产成人福利网站| 欧美激情精品久久久久久大尺度| 欧美精品一二区| 一本色道久久综合狠狠躁篇的优点| 日韩中文字幕在线看| 国产成人高清激情视频在线观看| 成人精品久久一区二区三区| 国产视频亚洲精品| 91欧美日韩一区| 成人国产在线激情| 国产精品久久久久aaaa九色| 国产一区二区三区四区福利| 91av在线播放视频| 久久久久久香蕉网|