【问题标题】:NSAnimationContext does not animate frame size for NSButtonNSAnimationContext 不会为 NSButton 设置动画帧大小
【发布时间】:2016-09-21 13:29:43
【问题描述】:

NSAnimationContext 文档中所示,使用NSAnimationContext.runAnimationGroup(_:_:) 对帧原点 大小进行动画处理对于某些视图类型(包括NSImageView)都可以正常工作。但是,对于 NSButton,它不会按预期工作,除非我在 动画之后添加显式帧大小更改

NSImageView 的动画帧大小

对于 NSImageView,以下内容按预期工作。它被移动到原点,并调整为 200x200:

NSAnimationContext.runAnimationGroup({(let context) -> Void in
    context.duration = 2.0
    // Get the animator for an NSImageView
    let a = self.theImage.animator()
    // Move and resize the NSImageView
    a.frame = NSRect(x: 0, y: 0, width: 200, height: 200)
}) {
    print("Animation done")
}

NSButton 的动画帧大小

当使用 NSButton 执行相同操作时,按钮会移动不会调整大小

NSAnimationContext.runAnimationGroup({(let context) -> Void in
    context.duration = 2.0
    // Get the animator for an NSButton
    let a = self.button.animator()
    // Move and resize the NSImageView
    a.frame = NSRect(x: 0, y: 0, width: 200, height: 200)
}) {
    print("Animation done")
}

但是,如果我将以下代码行添加到最后,在所有动画代码之后,它会按预期工作!

self.button.frame = NSRect(x: 0, y: 0, width: 200, height: 200)

NSButton 的最终工作清单是:

NSAnimationContext.runAnimationGroup({(let context) -> Void in
    context.duration = 2.0
    // Get the animator for an NSButton
    let a = self.button.animator()
    // Move and resize the NSImageView
    a.frame = NSRect(x: 0, y: 0, width: 200, height: 200)
}) {
    print("Animation done")
}
self.button.frame = NSRect(x: 0, y: 0, width: 200, height: 200)

我不是在这里寻找礼物马,但我不明白为什么 NSButton 需要这样做,甚至是什么使它起作用。谁能解释为什么在动画代码之后显式设置NSButton的框架使动画工作?

【问题讨论】:

    标签: swift macos cocoa animation nsanimationcontext


    【解决方案1】:

    我怀疑这与运行时生成的隐式自动布局约束有关。修改框架后,自动布局只是将其恢复为原始大小。

    我放弃了原来的方法,转而采用以下方法:

    1. 在 Interface Builder 中创建宽度和/或高度约束。我使用默认优先级 1000(约束是强制性的)。
    2. 为宽度和/或高度NSLayoutConstraint 创建一个出口。这在 IB 中很棘手:我必须在检查器的测量选项卡中双击约束,然后在检查器中打开约束对象。然后您可以选择连接选项卡并连接插座。
    3. 在我的NSViewController 子类中,我使用锚点来定义新的高度或宽度:theWidthConstraint.constant = 200 后跟self.view.needsUpdateConstraints = true

    这种方法更简洁,与自动布局系统更兼容。此外,它还可以轻松地为新的自动布局导致的整个布局更改设置动画:

    NSAnimationContext.runAnimationGroup({(let context) -> Void in
        context.duration = 1.0
        self.theWidthConstraint.animator().constant = 200
        // Other constraint modifications can go here
    }) {
        print("Animation done")
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-12-07
      • 1970-01-01
      • 1970-01-01
      • 2017-01-12
      • 2016-10-27
      • 1970-01-01
      相关资源
      最近更新 更多