CGAffineTransformMakeScale 不工作 - OS X - Cocoa

CGAffineTransformMakeScale not working - OS X - Cocoa

我正在开发一个简单的 Mac 应用程序。我希望能够在 NSButton 上应用转换并使其变大。其大小的两倍。但是我的代码不起作用,它只是将按钮滑动到一个角落。有谁知道哪里出了问题吗?

[NSAnimationContext runAnimationGroup:^(NSAnimationContext *context) {

    [numberButton1.animator.layer setAffineTransform:CGAffineTransformMakeScale(4.0, 4.0)];
    numberButton1.layer.anchorPoint = CGPointMake(0.5, 0.5);
    [numberButton1.animator.layer setAffineTransform:CGAffineTransformMakeScale(1.0, 1.0)];

} completionHandler:nil];

更新 1

我尝试了以下方法,但没有任何作用:(

   CGAffineTransform test = CGAffineTransformMakeScale(4.0, 4.0);

   [NSAnimationContext runAnimationGroup:^(NSAnimationContext *ctx) {
        numberButton1.animator.layer.affineTransform = test;
    } completionHandler:^{
        [NSAnimationContext runAnimationGroup:^(NSAnimationContext *ctx) {
            numberButton1.animator.layer.affineTransform = CGAffineTransformIdentity;
        } completionHandler:^{
            NSLog(@"Done...");
        }];
    }];

更新 2

这是我的代码 sudo,希望这会有所帮助:

我的头文件(.h)文件:

#import <Cocoa/Cocoa.h>
#import <QuartzCore/QuartzCore.h>

@interface ViewController : NSViewController {

    IBOutlet NSButton *numberButton1;
}

-(IBAction)demo:(id)sender;

@end

我的实现 (.m) 文件:

#import "ViewController.h"

@implementation ViewController

-(IBAction)demo:(id)sender {

    CGRect frame = numberButton1.layer.frame;
    CGPoint center = CGPointMake(CGRectGetMidX(frame), CGRectGetMidY(frame));
    numberButton1.layer.position = center;
    numberButton1.layer.anchorPoint = CGPointMake(0.5, 0.5);

    [NSAnimationContext runAnimationGroup:^(NSAnimationContext *context) {

        context.allowsImplicitAnimation = YES;
        [[NSAnimationContext currentContext] setDuration:0.2];
        numberButton1.animator.layer.affineTransform = CGAffineTransformMakeScale(4.0, 4.0);

    } completionHandler:^{

        [NSAnimationContext runAnimationGroup:^(NSAnimationContext *context) {

            context.allowsImplicitAnimation = YES;
            [[NSAnimationContext currentContext] setDuration:0.2];
            numberButton1.animator.layer.affineTransform = CGAffineTransformIdentity;

        } completionHandler:nil];
    }];
}

- (void)viewDidLoad {
    [super viewDidLoad];

    // Do any additional setup after loading the view.

    numberButton1.wantsLayer = YES;
    numberButton1.layerContentsRedrawPolicy = NSViewLayerContentsRedrawOnSetNeedsDisplay;
    numberButton1.layer.backgroundColor = [NSColor colorWithRed:(17/255.0) green:(145/255.0) blue:(44/255.0) alpha:1.0].CGColor;
}

- (void)setRepresentedObject:(id)representedObject {
    [super setRepresentedObject:representedObject];

    // Update the view, if already loaded.
}

@end

我也没有为我的UI文件使用Auto Layout

谢谢,丹。

CALayer 上的 affineTransform 属性 只是 transform 属性 的便利包装。在 layer-backed views 上,你不应该改变它。话虽如此,这是可能的。

您的第一个问题是您无法使用 NSAnimation 块为图层属性设置动画。您需要显式创建一个 CABasicAnimation 对象来表示变换动画并将其添加到层中。 编辑:我只记得实际上可以为图层属性设置动画。您需要在上下文中启用 allowsImplicitAnimation 属性。 属性 的预期目的是让您在不使用动画代理的情况下为视图属性设置动画,但副作用是它可以让您为隐式图层属性设置动画。

第二个问题,如前所述,如果您的视图是支持图层的,则您无法安全地在视图的图层上设置变换/锚点。 NSView 将在几何形状发生变化时重置图层的变换和锚点。如果视图是图层托管的,您可以修改这些属性,但这会带来一整批您很可能希望避免的问题。您可以使用一些 hacks 来避免此问题,但它们需要调配,并且对于您不拥有的任何视图(例如 NSButton)应该避免使用它们。

所以我要问了,为什么要把按钮做成两倍大?缩放状态是短暂的,还是持久的?如果它持续存在,请改为更改框架。否则,如果它是瞬态的并且视图的几何形状没有改变,您可以修改这两个属性,因为 AppKit 没有理由在您完成动画之前重置它们。


编辑:您看不到动画的原因是您的原始代码在同一个事务中应用了两次缩放变换。当此事务合并修改时,它将选择最后应用的变换,这意味着它将是恒等变换,顺便说一句,应该写成 CGAffineTransformIdentity 而不是因子为 1 的比例变换. 通过将另一个动画块放在第一个动画的完成块中,在新事务中应用按比例缩小的动画。例如:

[NSAnimationContext runAnimationGroup:^(NSAnimationContext *ctx) {
        ctx.allowsImplicitAnimation = YES;
        layer.affineTransform = transform;
    } completionHandler:^{
        [NSAnimationContext runAnimationGroup:^(NSAnimationContext *ctx) {
            ctx.allowsImplicitAnimation = YES;
            layer.affineTransform = CGAffineTransformIdentity;
        } completionHandler:nil];
}];

在尝试动画之前,确保要缩放的子视图的父视图是图层支持的 (wantsLayer = YES)。