CS193p Lecture 7 - Views, Gestures

Views

如何绘制自定义图像

 

Gestures

如何处理用户手势操作

 

Views

1、它是基本的构造块,代表屏幕上一块矩形区域,定义了一个坐标空间,在此空间中可以绘制,可以添加触控事件;

2、它是分层级的,可以在视图中嵌套视图;

3、一个视图只有一个父视图,但可以有多个子视图,视图就是一个个的矩形,可以重叠;

4、UIWindow,所有视图都展示在其中

iOS只有一个UIWindow(不像Mac application)

self.view.window

5、

添加子视图

(void)addSubview:(UIView *)aView;

移除子视图

(void)removeFromSuperview;

6、每个UIViewController都有一个属性

@property (nomatic, strong) UIView *view;

self.view是UIViewController的顶级UIView

 当View Controller创建时,这个view就被关联起来了

如图,这个名为view的outlet就关联到View

7、常用的初始化模版

- (void)setup{...}
- (void)awakeFromNib{ [self setup];}
- (void)initWithFrame:(CGRect)aRect{
    self = [super initWithFrame:aRect];
    [self setup];
    return self;
}

 - 初始化的操作在setup方法中定义;

 - 然后首先是要重写指定初始化方法,在其中调用setup;

 - 其次,需要在awakeFromNib中也调用setup,原因是当一个UIView从storyboard中释放时,调用的是awakeFromNib;如果是通过alloc、init...来初始化的话,那么调用的是指定初始化方法initWithFrame;aRect制定了在父视图中的相对位置;

 

 CGFloat

  浮点数,用来表示图像大小、坐标

CGPoint

  CGFloat x, y;

CGSize

  CGFloat width, height;

CGRect

  CGPoint origin;  CGSize size;

坐标原点在左上角;

绘制的单位都是点,而不是像素点; 

(Retina屏每个点=2像素点,非Retina屏每个点=1像素点)

 

3个与location和size有关的属性

(CGRect) frame:视图在父视图坐标中的位置和大小;

(CGRect) bounds:视图在视图本身坐标中的位置和大小;(位置就是原点(0,0))

(CGPoint) center:视图在父视图坐标中的中心点;

注意:

frame和bounds的差别不仅仅是原点不一样,当view旋转时,要包容视图的矩形变的比原视图要大,所有frame可以这样理解:它是在你的父视图坐标系中包含你的一个矩形; 

 

Create view in XCode

先拖出一个通用视图,然后到标示符检察器(identity inspector),修改它的类;(与创建一个自定义ViewController类似)

Create view in code

alloc & initWithFrame: (CGRect  frame)

或者 alloc & init (等同于 frame 为 CGRectZero,CGRectZero是原点、长、宽都为0)

 

drawRect : is invoked automaticall, never call it directly!!

drawRect是由系统调用的,用户不要自行调用;

When a view needs to be redrawn,use:
- (void)setNeedsDisplay;

 

1、Quartz库:Core Graphics

很多C函数,都是以CG开头,以context上下文作为第一参数

2、UIBezierPath类

可以绘制复杂形状组成一个大大路径,然后对其进行描边(stroke)或者填充(fill)

 

Core Graphics的基本流程

1. Get a context to draw into

2. Create path

3. Set colors, fonts, textures, linewidths, linecaps, etc.

4. Stroke or fill above-created paths

UIBezierPath类封装了上述全部过程

 

第一步:设置context上下文(相当于一张画布)

如果使用UIBezierPath来绘制,则不需要获取context,系统会自动获取;

若不得已要用CG函数来绘制,获取context的方法:

CGContextRef context = UIGraphicsGetCurrentContext();

举个🌰

CGContextRef context = UIGraphicsGetCurrentContext();
CGContextTranslateCTM(context, self.bounds.size.width, self.bounds.size.height);
CGContextRotateCTM(context, M_PI);

 

第二步:绘制好 path

UIBezierPath *path = [[UIBezierPath alloc] init];

[path moveToPoint:CGPointMake(75, 100)];

[path addLineToPoint:CGPointMake(160, 150)];

[path addLineToPoint:CGPointMake(10, 150)];

[path closePath];

 

第三步:设置path的属性(包括填充fill和描边stroke)

[[UIColor greenColor] setFill];

[[UIColor redColor] setStroke];

 

第四步:将path属性赋予path

[path fill];

[path stroke];

 

注意到:只有执行完第四步,才真正绘制完成;若只到第二步,此时的path只是一条没有粗细、颜色的路径,所以页面上海看不到;

 

Draw Text

NSAttributedString *text = ...;

[text drawAtPoint:(CGPoint)p];

 

Draw Image

UIImage *image = ...;

[image drawAtPoint:(CGPoint)p];

[image drawInRect:(CGRect)r];  // 拉伸图片以适应区域

[image drawAsPatternInRect:(CGRect)patRect];  //平铺图片以充满区域

 

UIGestureRecognizer

是所有手势操作类的基类,无法实例化,我们用到的都是它的子类

1、Adding a gesture recognizer to a UIView;

2、A method to "handle" that gesture when it happens;

 

UIPanGestureRecognizer

translationInView:

velocityInView:

setTranslation:inView:

 

@property (readonly) UIGestureRecognizerState state;

Began、Changed、Ended: for continus gestures like a pan(拖动) or pinch(捏合)

Recognized:for discrete gestures like a tap(点击) or swipe(滑动)

Failed、Canneled:手势操作中来电话等 

 

UIPinchGestureRecognizer(捏合、缩放)

scale:表示缩放比例,初始值1.0

velocity:缩放速度

UIRotationGestureRecognizer(旋转)

rotaton:表示旋转角度

velocity:旋转速度

UISwipeGestureRecognizer(滑动)

@property UISwipeGestureRecognizerDirection direction;

@property NSUInteger numberOfTouchesRequired;

 

posted @ 2015-04-21 22:54  mobilefeng  阅读(181)  评论(0编辑  收藏  举报