Chapter 10 手势 iOS 8 -Swift Programming cookBook 读书笔记

来源:互联网 发布:centos 6.9 编辑:程序博客网 时间:2024/05/23 23:22

概述

iOS可以对swipe(滑动), pinch(捏), pan(拖拽), tap(点), long-press(长按), and rotation(旋转)共6种手势进行检测。
手势识别必须驾到UIView的实例里面,一个view可以有多个手势识别。
基本步骤:

  1. 创建一个手势识别
  2. 添加到一个view上,用addGestureRecognizer
  3. 写一个方法,当手势发生的时候,运行这个方法。这个方法必须返回void,必须无参数或只接受一个UIGestureRecognizer的参数
  4. 当不需要手势的时候,移除掉,用removeGestureRecognizer

手势识别可以被分为2类:

  • 不连续的:当检测到手势的时候,结束检测,调用一次方法,比如,双击
  • 连续的:持续检测,不断调用方法,直到手势结束。比如旋转,手势开始于用户旋转时,结束于用户抬起手指。
    UIGestureRecognizer有一个属性叫state,不连续的和连续的手势有不同的state:
  • 不连续的:
    • UIGestureRecognizerStatePossible
    • UIGestureRecognizerStateRecognized:认出手势
    • UIGestureRecognizerStateFailed:手势失败
  • 连续的:
    • UIGestureRecognizerStatePossible
    • UIGestureRecognizerStateBegan
    • UIGestureRecognizerStateChanged
    • UIGestureRecognizerStateEnded
    • UIGestureRecognizerStateFailed
    • UIGestureRecognizerStateCancelled,比如在手势过程中,有一个电话打过来

10.1 检测Swipe(滑动)

用UISwipeGestureRecognizer,一次只能检测一个方向:

var swipeRecognizer: UISwipeGestureRecognizer!    override func viewDidLoad() {        super.viewDidLoad()        swipeRecognizer = UISwipeGestureRecognizer(target: self, action: "handleSwipes:")        //只会检测向左的手势        swipeRecognizer.direction = .Left        swipeRecognizer.numberOfTouchesRequired = 1        view.addGestureRecognizer(swipeRecognizer)    }    func handleSwipes(sender: UISwipeGestureRecognizer) {        if sender.direction == .Down {            println("Down")        }        if sender.direction == .Left {            println("Left")        }        if sender.direction == .Right {            println("Right")        }        if sender.direction == .Up {            println("Up")        }    }

10.2 旋转

是属于连续的手势,用UIRotationGestureRecognizer, 不需要关心被旋转物体本来的角度,因为旋转时返回的角度都是基于0的。是一个相对的角度。

    var helloWorldLabel = UILabel()    var rotaionRecognizer: UIRotationGestureRecognizer!    var rotationAngleInRadians = 0.0 as CGFloat    helloWorldLabel.text = "Hello, World"    helloWorldLabel.font = UIFont.systemFontOfSize(16)    helloWorldLabel.sizeToFit()    helloWorldLabel.center = view.center    view.addSubview(helloWorldLabel)    rotaionRecognizer = UIRotationGestureRecognizer(target: self, action: "handleRotation:")    view.addGestureRecognizer(rotaionRecognizer)
func handleRotation(sender:UIRotationGestureRecognizer) {        println("\(sender.rotation) \(rotationAngleInRadians)")        helloWorldLabel.transform = CGAffineTransformMakeRotation(rotationAngleInRadians + sender.rotation)        if sender.state == .Ended {            rotationAngleInRadians += sender.rotation        }    }

如果要在模拟器上模拟,要按住option键。

10.3 检测Pan(拖动)

属于连续手势,在End状态的时候,可能取到的位置是一个nil值:

{    var panGestureLabel: UILabel!    var panGestureRecognizer: UIPanGestureRecognizer!//pan gesture        let labelFrame = CGRect(x: 0, y: 0, width: 150, height: 100)        panGestureLabel = UILabel(frame: labelFrame)        panGestureLabel.userInteractionEnabled = true        panGestureLabel.text = "Pan Gesture"        panGestureLabel.backgroundColor = UIColor.blackColor()        panGestureLabel.textColor = UIColor.whiteColor()        panGestureLabel.textAlignment = .Center        panGestureRecognizer = UIPanGestureRecognizer(target: self, action: "handlePanGestures:")        view.addSubview(panGestureLabel)        panGestureRecognizer.minimumNumberOfTouches = 1        panGestureRecognizer.maximumNumberOfTouches = 1        panGestureLabel.addGestureRecognizer(panGestureRecognizer)    }    func handlePanGestures(sender: UIPanGestureRecognizer) {        if sender.state != .Ended && sender.state != .Failed {            let location = sender.locationInView(sender.view!.superview)            sender.view?.center = location        }//        如果是多手指用这个//        sender.locationOfTouch(<#touchIndex: Int#>, inView: <#UIView?#>)    }

10.4 长按

用UILongPressGestureRecognizer, 有几个属性需要注意:

  • numberOfTapsRequired: 在启动这个手势需要的点击数目,tap的意思是放手指在屏幕上,然后离开,缺省是0
  • numberOfTouchesRequired:touch的手指数目
  • allowableMovement:手指在屏幕上移动的pixel的最大数目
  • minimumPressDuration:手势触发的最短按压时间
//长按        dummyButton = UIButton.buttonWithType(.System) as! UIButton        dummyButton.frame = CGRect(x: 0, y: 0, width: 72, height: 37)        dummyButton.setTitle("My Button", forState: .Normal)        longPressGestureRecognizer = UILongPressGestureRecognizer(target: self, action: "handleLongPressGestures:")        longPressGestureRecognizer.numberOfTouchesRequired = 2        //在识别的时候,容许有一些抖动        longPressGestureRecognizer.allowableMovement = 100        //要按多久        longPressGestureRecognizer.minimumPressDuration = 1        dummyButton.frame = CGRect(x: 100, y: 100, width: 100, height: 50)        view.addGestureRecognizer(longPressGestureRecognizer)        view.addSubview(dummyButton)
func handleLongPressGestures(sender: UILongPressGestureRecognizer) {        if sender.numberOfTouches() == 2 {            let touchPoint1 = sender.locationOfTouch(0, inView: sender.view)            let touchPoint2 = sender.locationOfTouch(1, inView: sender.view)            let midPointX = (touchPoint1.x + touchPoint2.x) / 2.0            let midPointY = (touchPoint1.y + touchPoint2.y) / 2.0            let midPoint = CGPoint(x: midPointX, y: midPointY)            dummyButton.center = midPoint        }    }

10.5 检测tap 手势

用UITapGestureRecognizer,相关的属性:
- numberOfTapsRequired: 在启动这个手势需要的点击数目,tap的意思是放手指在屏幕上,然后离开,缺省是0
- numberOfTouchesRequired:touch的手指数目

10.6 检测Pinch(捏)手势

用UIPinchGestureRecognizer:

//Pinch        let labelRect = CGRect(x: 200, y: 400, width: 50, height: 50)        pinchLabel = UILabel(frame: labelRect)        pinchLabel.backgroundColor = UIColor.blackColor()        pinchLabel.userInteractionEnabled = true        pinchGestureRecognizer = UIPinchGestureRecognizer(target: self, action: "handlePinches:")        pinchLabel.addGestureRecognizer(pinchGestureRecognizer)        view.addSubview(pinchLabel)
func handlePinches(sender: UIPinchGestureRecognizer) {        if sender.state == .Ended {            currentScale = sender.scale        } else if sender.state == .Began && currentScale != 0.0 {            sender.scale = currentScale        }        if sender.scale != CGFloat.NaN && sender.scale != 0.0 {            sender.view!.transform = CGAffineTransformMakeScale(sender.scale, sender.scale)        }    }

10.7 检测屏幕边缘的拖动手势

检测用户的手从屏幕的一边移动到你的view里面。比如划出上面的notification center和下面的控制中心。

func handleScreenEdgePan(sender: UIScreenEdgePanGestureRecognizer){if sender.state == .Ended{ displayAlertWithTitle("Detected",          message: "Edge swipe was detected")      }}init(coder aDecoder: NSCoder!) {super.init(coder: aDecoder)      /* Create the Pinch Gesture Recognizer */screenEdgeRecognizer = UIScreenEdgePanGestureRecognizer(target: self, action: "handleScreenEdgePan:")      /* Detect pans from left edge to the inside of the view */      screenEdgeRecognizer.edges = .Left    }
0 0
原创粉丝点击