Pan Segue调用viewDidLoad Loop

时间:2015-12-09 00:33:22

标签: ios swift uibutton uipangesturerecognizer

我的平移手势以编程方式假按下按钮。如果你按下实际按钮,VC的viewDidLoad会再次运行一次,停止并且没问题。 但是当我使用pan-gesture以编程方式假按下按钮时,viewDidLoad会运行大约七次,然后停止。

右边手势会触发"明天"加载了几次的状态。此时,左边的手势会触发"今天"州。这也加载了4-5次。

有什么想法吗?如果需要,下面有一些代码。

在viewDidLoad中添加了平移手势:

    //Adds edge gesture depending on VC state
    if curMainList == "Today" {
        let panLeftEdgeGesture_MainVC = UIScreenEdgePanGestureRecognizer(target: self, action: "panLeftEdge_toLifeList:")
        panLeftEdgeGesture_MainVC.edges = .Left
        view.addGestureRecognizer(panLeftEdgeGesture_MainVC)

        let panRightEdgeGesture_MainVC = UIScreenEdgePanGestureRecognizer(target: self, action: "panFromRightEdgeAction:")
        panRightEdgeGesture_MainVC.edges = .Right
        view.addGestureRecognizer(panRightEdgeGesture_MainVC)

        self.footer_LeftBtn.addTarget(self, action: "LeftFooterBtnPress", forControlEvents: UIControlEvents.TouchUpInside)
    }
    else {
        let panLeftEdgeGesture = UIScreenEdgePanGestureRecognizer(target: self, action: "panFromLeftEdgeAction:")
        panLeftEdgeGesture.edges = .Left
        view.addGestureRecognizer(panLeftEdgeGesture)
    }

手势被触发:

//Gestures visible when view is 'Today'
func panLeftEdge_toLifeList(sender: UIScreenEdgePanGestureRecognizer) {
    dispatch_async(dispatch_get_main_queue()) { () -> Void in
        self.performSegueWithIdentifier("segueToLifeLists", sender: nil)
    }
}

func panFromRightEdgeAction(sender: UIScreenEdgePanGestureRecognizer) {
    //self.tomHdrBtnPress(tomorrowHdr)
    tomorrowHdr.sendActionsForControlEvents(UIControlEvents.TouchUpInside)
}

//Gesture added when viewing 'Tomorrow' list
func panFromLeftEdgeAction(sender: UIScreenEdgePanGestureRecognizer) {
    //self.todayHdrBtnPress(todayHdr)
    todayHdr.sendActionsForControlEvents(UIControlEvents.TouchUpInside)
}

@IBAction func todayHdrBtnPress(sender: AnyObject) {
    UIView.animateWithDuration(0.75, animations: {
        //Header changes
        self.hdrBox.backgroundColor = UIColor(red: 46/255.0, green: 173/255.0, blue: 11/255.0, alpha: 1.0)
        self.footer_RightArrow.hidden = false
        self.footer_RightBtn.hidden = false
        }
        , completion: nil
    )
    curMainList = "TodayTask"
    currentListEntity = curMainList
    viewDidLoad()
}

@IBAction func tomHdrBtnPress(sender: AnyObject) {
    UIView.animateWithDuration(0.75, animations: {
        //Header changes
        self.hdrBox.backgroundColor = UIColor(red: 49/255.0, green: 82/255.0, blue: 171/255.0, alpha: 1.0)
        self.footer_LeftBtn.addTarget(self, action: "LeftFooterBtnPress", forControlEvents: UIControlEvents.TouchUpInside)
        }
        , completion: nil
    )
    curMainList = "TomTask"
    currentListEntity = curMainList
    viewDidLoad()
}

1 个答案:

答案 0 :(得分:1)

问题是平移手势是连续手势(意味着当您移动手指时,会重复调用处理程序)。对于平移手势,用gesture.state .Began调用一次,当用户的手指移动时,state .Changed重复一次当用户停止手势时,最后使用state .Ended.Cancelled

因此,您通常不会从连续手势触发animateWithDuration。您只需根据gesture.translationInView()或您拥有的内容更新状态。只需立即更新视图以反映更新的平移,并且它经常被调用,它最终会呈现感觉像动画的东西,但它实际上只是一系列与持续更新流相关的更新当用户进行手势时,您的手势识别器处理程序会收到。

在连续手势中进行动画处理的唯一时间是.Ended.Cancelled,以完成动画。例如,也许用户将手指拖到中途,所以在.Changed上你只需立即更新视图而不进行任何动画,但当他们抬起手指时(即手势处理程序接收.Ended),你可以动画完成视图的最终状态。

最重要的是,手势识别器中的处理是一种非常不同的动画机制,可能是一个按钮(在其中您调用animateWithDuration方法一次以启动UIKit随后为您处理的动画) 。最好不要将这两种非常不同的更新/动画UI方式混为一谈。

您还在其中一个平移处理程序中执行segue。如果您希望在平移时以交互方式执行segue,则应参考WWDC 2013视频Custom Transitions Using View Controllers,其中显示了如何将动画控制器(它决定动画的本质)与交互控制器(其中将手势的进度与动画控制器链接起来。但是在这种模式中,你只执行一次segue,只更新手势中的UIPercentDrivenInteractiveTransition,这将把过渡的进度与用户的手指联系起来。 `