连续执行UIView的animateWithDuration:delay:options:animations:completion出现的问题

  • 问题背景

自定义实现UIKeyboard的accessoryView的基本原理是根据UIKeyboard的frame来动态调整accessoryView的frame值,为了能达到accessoryView的平滑的变动,我们用UIView的类方法animateWithDuration:delay:options:animations:completion:来动态调整accessoryView的frame值

  • 问题出现描述

我们根据通知UIKeyboardWillShowNotification来触发调用animateWithDuration:delay:options:animations:completion:,那么问题来了,当UITextField的属性autocorrectionType设置为UITextAutocorrectionTypeYes(也就是在中文系统下唤起键盘的时候会自动切换为中文键盘),并且在首次打开键盘的时候,系统会发送多次UIKeyboardWillShowNotification通知,从而会多次触发调用animateWithDuration:delay:options:animations:completion:,先来看看代码:

  

这段代码会被多次连续执行,照理对self.frame(self对应accessoryView)的改变只需在animations的block中处理即可,但是代码的原作者不知道出于什么目的在competion中也同样执行了一遍,来看一下NSLog中的内容:

关注下每次selfEndingRect的frame的y轴值,我们期望的最终值是276,但是看到completion中的selfEndingRect的frame的y轴值的顺序刚好相反,最终值为312,也就是第一次调用时候的值,导致accessoryView的最终展现的位置要比预期的偏下36

  •  问题分析

一些无用的分析过程就不累述了,看看最终的结果分析就好,先来写一段测试代码,循环执行多次animate操作,每次动画执行时间为10秒

再来看一下log:

 

分析下不难发现,第0次animate操作的completion最后执行,也就是10秒动画执行的时间后,后面的4次animate直接被cancel了,从时间上也可以发现,animate的开始时间和completion的结束时间都是在大约47秒的时候,两者相差0.*秒的时间,远小于设置的10秒动画时间,这里比较奇怪的一点是既然被cancel了,但是finish的值为什么还是为YES

  • 解决方法

        就本例来说,去掉completion中对frame的赋值就可以了

一般来说不太会出现本例一样循环进行animate操作,如果要实现连续的动画,简单方法就是在completion继续执行animate,以保证下一个animation是在上一个完成的基础上执行的

时间: 2024-10-28 15:41:43

连续执行UIView的animateWithDuration:delay:options:animations:completion出现的问题的相关文章

UIViewController新方法的使用(transitionFromViewController:toViewController:duration:options:animations:completion:)

iOS5中,UIViewController新添加了几个方法: - (void)addChildViewController:(UIViewController *)childController NS_AVAILABLE_IOS(5_0); - (void) removeFromParentViewController NS_AVAILABLE_IOS(5_0); - (void)transitionFromViewController:(UIViewController *)fromView

第七篇、使用UIView的animateWithDuration方法制作简易动画

import UIKit class LolitaCircleButton: UIButton { private var color: UIColor private var imageURL: String init(color: UIColor , imageURL: String) { self.color = color self.imageURL = imageURL super.init(frame: CGRectZero) commonInit() layer.shadowOpa

animateWithDuration:animations:completion:

Creates an animation block object that can be used to set up keyframe-based animations for the current view. Declaration (void)animateKeyframesWithDuration:(NSTimeInterval)duration delay:(NSTimeInterval)delay options:(UIViewKeyframeAnimationOptions)o

Linux 连续执行多条命令

每条命令使用";"隔开,则无论前边的命令执行成功与否都会继续执行下一条命令 这里,故意将第二条命令中的echo多写了一个o,命令执行出错,但并不影响后续命令的执行 可以这么想,如果用分号来间隔命令,就相当于将命令分隔在了不同的行,无论前一行的命令成功或失败,都不影响下一行命令的执行. $ echo 1; echoo 2; echo 3; echo 4 1 -bash: echoo: command not found 3 4 若命令间使用"&&"隔开

shell脚本linux命令连续执行

shell命令连续执行的三种方式: 1.命令1:命令2:命令3 依次执行命令,无论前一条命令是否执行成功. 2.命令1 && 命令2 && 命令3 前一条命令执行成功后才会执行下一条命令. 3.命令1 || 命令2 || 命令3 前一条命令执行失败才会执行下一条命令. 原文地址:https://www.cnblogs.com/smallredness/p/9241775.html

Linux 连续执行多条命令的方法

多个命令可以放在一行上,其执行情况得依赖于用在命令之间的分隔符. 如果每个命令被一个分号 (;) 所分隔,那么命令会连续的执行下去,如: 引用 [email protected]:/proc> printf "%s/n" "This is executed" ; printf "%s/n" "And so is this"This is executedAnd so is this 如果每个命令被 && 

解决CMD命令不能连续执行的问题

前一段时间用批处理文件(.bat或.cmd)写项目构建脚本,发现一个奇怪的问题. 就是几条不同的构建命令,比如下面两条: coffee -c src/ jade -P demo/ 这两条命令每条都可以正常执行.但是当我把这几条命令放到一个批处理脚本文件中执行的时候却不能顺利执行完毕,脚本程序在执行完第一条命令的时候就自动终止了. 对于这个问题,我很是纳闷,不知道问题究竟在哪里.我想这可能是我自己的一个个例,所以暂时只能为每一条指令都设立一个脚本文件,然后每次都按顺序手动运行. 后来呢,我越来越觉

Python实现cmd命令连续执行

之前是想写一个微信控制程序,通过登录网页微信,可以直接执行命令行代码.也不用ssh登录了,想法很方便. 但是现实很残酷,微信登录这块基本没有问题,已经有大佬写好了,但是命令行执行遇到问题了. 运行cmd 开始时,使用os.popen()执行命令,但是该命令需要手动修改运行目录.此方案被我直接丢弃了. 单开进程 那么自然想到通过启动进程的方式来实现,Python有对进程的封装subprocess,可以通过创建Popen对象来实现.我只要单开一个bash,与它进行交互就好啦. 简单实现如下: ? p

[New learn]动画-基于UIView

原文:https://developer.apple.com/library/ios/documentation/WindowsViews/Conceptual/ViewPG_iPhoneOS/AnimatingViews/AnimatingViews.html 代码:https://github.com/xufeng79x/ViewBaseAnimation 1.简介 Animation,源于拉丁语,意为给无生命的物体注入灵魂. 动画可以为app应用增色不少,提高用户体验. 我们一般使用UIK