ios拦截动画值

发布于 2025-01-03 18:05:04 字数 1751 浏览 7 评论 0原文

[UIView animatWithDuration...] 的 ios 动画期间,如何在动画期间拦截动画值?

这是我当前(不起作用)的解决方案:

#import "FooterSelectionView.h"
#import <QuartzCore/QuartzCore.h>

@implementation FooterSelectionView

@synthesize displayLink;

- (id)initWithCoder:(NSCoder *)aDecoder
{
    self = [super initWithCoder:aDecoder];
    if (self) {
        // Initialization code
        
        selector = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"selector.png"]];
        [self addSubview:selector];
        
        [self setSelectorFrame:CGRectMake(700, 0, selector.frame.size.width, selector.frame.size.height)];
    }
    return self;
}

- (void)drawRect:(CGRect)rect
{
    UIImage *bg = [UIImage imageNamed:@"overlayArea.png"];
    [bg drawInRect:CGRectMake(0, 0, 957, 127) blendMode:kCGBlendModeNormal alpha:1];
    
    [selector.image drawInRect:selector.frame blendMode:kCGBlendModeOverlay alpha:1];
}

-(void)step {
    [self setNeedsDisplay];
    
    NSLog(@"%@", @"step");
}

- (void)setSelectorFrame:(CGRect)frame {
    displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(step)];
    [displayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
    
    [UIView animateWithDuration:5 animations:^{
        selector.frame = frame;
        //self.alpha = 0
    } completion:^(BOOL finished){
        [self setNeedsDisplay];
        
        [self.displayLink invalidate];
        self.displayLink = nil;
        NSLog(@"%@", @"stop");
    }];
}

@end

我看到实际的图像视图移动,但带有叠加层的“绘制”版本仅立即到达目标值。我希望能够告诉“绘制”版本去往实际选择器视图所在的位置。我该怎么做?

编辑

当我 NSLog selector.frame.origin.x 时,我注意到该值始终为 0。我可以看到屏幕上的选择器是动画,那么是什么给出了呢?

during an ios animation of [UIView animatWithDuration...] how can I intercept the animation values during the animation?

Here's my current (not working) solution:

#import "FooterSelectionView.h"
#import <QuartzCore/QuartzCore.h>

@implementation FooterSelectionView

@synthesize displayLink;

- (id)initWithCoder:(NSCoder *)aDecoder
{
    self = [super initWithCoder:aDecoder];
    if (self) {
        // Initialization code
        
        selector = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"selector.png"]];
        [self addSubview:selector];
        
        [self setSelectorFrame:CGRectMake(700, 0, selector.frame.size.width, selector.frame.size.height)];
    }
    return self;
}

- (void)drawRect:(CGRect)rect
{
    UIImage *bg = [UIImage imageNamed:@"overlayArea.png"];
    [bg drawInRect:CGRectMake(0, 0, 957, 127) blendMode:kCGBlendModeNormal alpha:1];
    
    [selector.image drawInRect:selector.frame blendMode:kCGBlendModeOverlay alpha:1];
}

-(void)step {
    [self setNeedsDisplay];
    
    NSLog(@"%@", @"step");
}

- (void)setSelectorFrame:(CGRect)frame {
    displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(step)];
    [displayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
    
    [UIView animateWithDuration:5 animations:^{
        selector.frame = frame;
        //self.alpha = 0
    } completion:^(BOOL finished){
        [self setNeedsDisplay];
        
        [self.displayLink invalidate];
        self.displayLink = nil;
        NSLog(@"%@", @"stop");
    }];
}

@end

I see the actual image view move, but the "drawn" version with overlay only goes immediately to the target value. I'd like to be able to tell the "drawn" version to go wherever the actual selector view is. How can I do this?

edit

When I NSLog the selector.frame.origin.x I've noticed that the value is always 0. I can see that the selector is animation on the screen, so what gives?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

老子叫无熙 2025-01-10 18:05:04

这里有一些错误:

  1. 不要尝试用drawRect做逐帧动画,它确实不够快,因为核心显卡没有硬件加速(它在模拟器上可能看起来很好 - 它赢了)不在真实设备上)。

    如果您想要为图像的矩形设置动画,请使用 UIImageView 并使用普通的 UIView 动画方法为其设置动画。

    如果您找不到使用普通动画方法实现动画的方法,您可以使用 displayLink 逐帧完成,但您仍然应该通过更新 UIImageView 的帧而不是绘制图像来进行绘制直接在drawRect中。

  2. UIView 动画不会直接为 view.frame 属性设置动画。如果您设置了 view.frame,它会立即设置为您指定的任何值,即使在动画时也是如此。尝试将逐帧动画同步到另一个视图的帧,因为它会产生动画效果,这是行不通的。

    要获取动画视图框架的实际动画中间值,您需要查看 view.layer.presentationLayer.frame - 这是动画值。 view.frame 实际上只是一个返回 view.layer.modelLayer.frame 的 getter 方法,它始终设置为任何值 view.frame 最后设置为。

There's a few mistakes here:

  1. Don't try to do frame-by-frame animation with drawRect, it's really not fast enough for this because Core Graphics isn't hardware accelerated (it may look fine on the simulator - it won't on a real device).

    If you want to animate an image's rectangle, use a UIImageView and animate it with normal UIView animation methods.

    If you can't see a way to achieve your animation using normal animation methods, you can do it frame by frame using displayLink, but you should still do your drawing by just updating the frame of a UIImageView instead of drawing the image directly in drawRect.

  2. UIView animation doesn't animate the view.frame property directly. If you set the view.frame it sets immediately to whatever value you specify, even when animating. Trying to sync a frame-by-frame animation to the frame of another view as it animates therefor won't work.

    To get the actual mid-animation value of the animating view frame, you need to look at the view.layer.presentationLayer.frame instead - this is the value that animates. The view.frame is actually just a getter method that returns the view.layer.modelLayer.frame, which is always set to whatever value view.frame was last set to.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文