如何在更改uiview的隐藏模式时添加动画?
Posted
技术标签:
【中文标题】如何在更改uiview的隐藏模式时添加动画?【英文标题】:How to add animation while changing the hidden mode of a uiview? 【发布时间】:2011-09-04 20:45:12 【问题描述】:我想在更改其隐藏模式时向视图添加动画,即
my_view.hidden=YES;
我在导航栏中添加了一个按钮。当我们单击它时,新视图设置为取消隐藏。它绘制在导航表的上方。
【问题讨论】:
你想要什么样的动画,例如淡入淡出、翻转等? 【参考方案1】:将视图的不透明度从 100% 设置为 0%。让动画完成回调将视图设置为隐藏。您可能还希望在回调期间将不透明度重置为 100%,以便在取消隐藏时视图将显示为完全不透明。
yourView.alpha = 0.0 //for zero opacity
yourView.alpha = 1.0 //for 100% opacity
【讨论】:
如果 w 在此之前需要使用 alpha,为什么要隐藏呢?使用 alpha 会降低性能,我们不会使用这种方法来避免这种情况。【参考方案2】:但是没有隐藏动画;使用下面的 Swift 代码可以得到相同的结果:
UIView.animate(withDuration: 0.2, delay: 0, options: [], animations:
self.yourView.alpha = 0 // Here you can change the alpha property of the view
, completion: _ in
self.yourView.isHidden = true // Here you hide it when animation done
)
【讨论】:
太棒了,简单。谢谢! 出现错误:nil 与预期的参数类型“UIViewAnimationOptions”不兼容。我正在使用 Xcode 7.3.1。 @JayprakashDubey 你可以用options: []
替换options: nil
这可能应该是选择的答案(实际上可能不是因为 OP 在 Obj-C 时代发布了这个),这很简洁,完全符合 OP/我自己的需要【参考方案3】:
不幸的是,hidden 不是一个可以通过 UIView 动画设置动画的属性。我认为你最好的选择可能是使用@Erik B 建议的动画之一,或者开始涉足更强大的核心动画。浏览一下 UIView 动画和核心动画的文档。
通过使用 UIView 动画从另一个视图下方滑动新视图,我实现了类似于您的建议。这使它看起来像一个滑出的抽屉。如果你想做这样的事情,你需要拦截 touch up inside 事件并将动画代码放在那里。
- (IBAction)buttonClicked:(id)sender
[UIView animateWithDuration:0.5
delay:0.0
options:UIViewAnimationCurveEaseOut
animations:^(void)
self.myView.frame = /* set the frame here */
completion:NULL];
【讨论】:
选项应该是:UIViewAnimationOptionCurveEaseInOut
【参考方案4】:
我认为更合适的做法是:
[UIView transitionWithView:aView
duration:0.3
options:UIViewAnimationOptionTransitionCrossDissolve
animations:^(void)
aView.hidden = NO;
completion:nil];
【讨论】:
这是正确答案,不需要弄乱 alpha。我已经把它整理好了,这样更清晰。【参考方案5】:更新到 Swift 3:
UIView.animate(withDuration: 0.2, delay: 0.2, options: .curveEaseOut,
animations: firstView.alpha = 0,
completion: _ in firstView.isHidden = true
//Do anything else that depends on this animation ending
)
如果您希望在第一个视图消失后重新制作动画,您可以使用 alpha = 1
和 hidden = false
复制完成块内的代码。
【讨论】:
【参考方案6】:这是我写的一个类别,用于在 UIView 上引入一个新的“隐藏”属性,它正确支持动画:
@implementation UIView (AnimateHidden)
-(void)setHiddenAnimated:(BOOL)hide
[UIView animateWithDuration:0.5
delay:0.0
options: UIViewAnimationCurveEaseOut
animations:^
[UIView setAnimationCurve:UIViewAnimationCurveEaseInOut];
if (hide)
self.alpha=0;
else
self.hidden= NO;
self.alpha=1;
completion:^(BOOL b)
if (hide)
self.hidden= YES;
];
@end
【讨论】:
谢谢,这对我有用!但我做了一些补充以使其与hidden
属性互操作:基本上,始终将alpha
保留在最后的1.0,结束设置正确的起始alpha
和hidden
。【参考方案7】:
这是更正的 N.J. 版本:
@implementation UIView (AnimateHidden)
-(void)setHiddenAnimated:(BOOL)hide duration:(NSTimeInterval)duration
if(self.hidden == hide)
return;
if(hide)
self.alpha = 1;
else
self.alpha = 0;
self.hidden = NO;
[UIView animateWithDuration:duration animations:^
if (hide)
self.alpha = 0;
else
self.alpha = 1;
completion:^(BOOL finished)
if(finished)
self.hidden = hide;
];
@end
【讨论】:
【参考方案8】:这是 swift 版本:
斯威夫特 2
UIView.animateWithDuration(0.5, delay: 0.2, options: UIViewAnimationOptions.CurveEaseOut, animations:
objView.alpha = 0
, completion: finished in
objView.hidden = true
)
斯威夫特 3、4、5
UIView.animate(withDuration: 0.5, delay: 0.2, options: UIView.AnimationOptions.curveEaseOut, animations:
objView.alpha = 0
, completion: finished in
objView.isHidden = true
)
这将执行持续时间为 5 秒并延迟 2 秒后的动画。
可用的动画选项是:
CurveEaseInOut, CurveEaseIn, CurveEaseOut, CurveLinear
【讨论】:
【参考方案9】:由于其中一些答案有点混乱,我想我可以发布我对该 API 的简约设计。我还添加了延迟和持续时间 - 为什么不呢。
在我们的实现中。
#import "UIView+AnimateHidden.h"
@implementation UIView (AnimateHidden)
- (void)setHiddenAnimated:(BOOL)hide
delay:(NSTimeInterval)delay
duration:(NSTimeInterval)duration
[UIView animateWithDuration:duration
delay:delay
options:UIViewAnimationOptionAllowAnimatedContent
animations:^
if (hide)
self.alpha = 0;
else
self.alpha = 0;
self.hidden = NO; // We need this to see the animation 0 -> 1
self.alpha = 1;
completion:^(BOOL finished)
self.hidden = hide;
];
@end
在我们的 header 文件中。
#import <UIKit/UIKit.h>
@interface UIView (AnimateHidden)
- (void)setHiddenAnimated:(BOOL)hide
delay:(NSTimeInterval)delay
duration:(NSTimeInterval)duration;
@end
【讨论】:
【参考方案10】:NJ 和 Stanislav 的答案在这里帮助我为此创建了一个新类别,我认为这改进了他们的答案,所以我想我会发布我想出的东西以防它帮助其他人。
请注意,它仅在 ios4 或更高版本中使用,因为它使用块。
UIView+AnimateHidden.m
#import "UIView+AnimateHidden.h"
@implementation UIView (AnimateHidden)
- (void)setHidden:(BOOL)hidden animated:(BOOL)animated
// If the hidden value is already set, do nothing
if (hidden == self.hidden)
return;
// If no animation requested, do the normal setHidden method
else if (animated == NO)
[self setHidden:hidden];
return;
else
// Store the view's current alpha value
CGFloat origAlpha = self.alpha;
// If we're unhiding the view, make it invisible initially
if (hidden == NO)
self.alpha = 0;
// Unhide the view so we can see the animation
self.hidden = NO;
// Do the animation
[UIView animateWithDuration:0.5
delay:0.0
options: UIViewAnimationOptionCurveEaseOut
animations:^
// Start animation block
if (hidden == YES)
self.alpha = 0;
else
self.alpha = origAlpha;
// End animation block
completion:^(BOOL b)
// Start completion block
// Finish up by hiding the view if necessary...
self.hidden = hidden;
// ... and putting back the correct alpha value
self.alpha = origAlpha;
// End completion block
];
@end
【讨论】:
查看 Abhi 对新 API 的回答,它使这变得更简单,无需触及 alpha 值。【参考方案11】:如果您希望使用更复杂的动画类型或 UIView 不支持的动画,则可以使用另一个版本
- (void)setHidden:(BOOL)hidden withAnimationDuration:(NSTimeInterval)duration
CATransition* transition = (
CATransition* its = [CATransition animation];
its.duration = duration;
its.timingFunction =
[CAMediaTimingFunction
functionWithName: kCAMediaTimingFunctionEaseInEaseOut];
its.type = kCATransitionPush;
its.subtype = (hidden ? @"fromBottom" : @"fromTop");
its
);
UIView* containerView = self.superview;
[containerView.layer removeAllAnimations];
[containerView.layer addAnimation: transition forKey: kCATransition];
self.hidden = hidden;
if (!hidden)
[self.superview bringSubviewToFront: self];
【讨论】:
【参考方案12】:这是我用来在“显示更多...”和“显示更少...”按钮单击时为视图“增长”和“缩小”建模的代码。模仿 Palyancodr 的答案
这种方法允许我在故事板中创建两个视图,以便约束在不同的 iOS 设备上按预期工作,我不需要自定义所有约束的代码。
@IBAction func showMoreOrLessAction(_ sender: Any)
// if small view showing
if showMoreLargeView.isHidden
showMoreSmallView.isHidden = true
//showMoreLargeView.isHidden = false
UIView.animate(withDuration: 0.2, delay: 0, options: [], animations:
self.showMoreLargeView.alpha = 1 // Here you will get the animation you want
, completion: _ in
self.showMoreLargeView.isHidden = false // Here you hide it when animation done
)
else // large view showing
//showMoreSmallView.isHidden = false
UIView.animate(withDuration: 0.2, delay: 0, options: [], animations:
self.showMoreSmallView.alpha = 1 // Here you will get the animation you want
, completion: _ in
self.showMoreSmallView.isHidden = false // Here you hide it when animation done
)
showMoreLargeView.isHidden = true
【讨论】:
以上是关于如何在更改uiview的隐藏模式时添加动画?的主要内容,如果未能解决你的问题,请参考以下文章