【问题标题】:Translating NSConstraints From Objective-C to Swift将 NSConstraints 从 Objective-C 转换为 Swift
【发布时间】:2015-04-08 20:10:36
【问题描述】:

我希望将基于 Objective-c 的通用应用程序转变为 Swift 项目。到目前为止,我已经能够交换大部分代码,但在翻译以下内容时遇到了问题:

NSLayoutConstraint *leftConstraint = [NSLayoutConstraint constraintWithItem:self.contentView
                                                                  attribute:NSLayoutAttributeLeading
                                                                  relatedBy:0
                                                                     toItem:self.view
                                                                  attribute:NSLayoutAttributeLeft
                                                                 multiplier:1.0
                                                                   constant:0];
[self.view addConstraint:leftConstraint];

NSLayoutConstraint *rightConstraint = [NSLayoutConstraint constraintWithItem:self.contentView
                                                                   attribute:NSLayoutAttributeTrailing
                                                                   relatedBy:0
                                                                      toItem:self.view
                                                                   attribute:NSLayoutAttributeRight
                                                                  multiplier:1.0
                                                                    constant:0];
[self.view addConstraint:rightConstraint];

我也必须更改此代码:

- (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer
{
    return NO;
}

在 Swift 中有类似的方法吗?

任何帮助将不胜感激。提前感谢所有回复的人。 :)

【问题讨论】:

  • 尝试研究 Masonry 之类的框架,手动添加约束实在是一件苦差事
  • 出于好奇......为什么我问这个问题会失去两个声誉?
  • 人们倾向于在他们认为提出问题的人没有在首先研究问题方面付出足够努力的情况下对问题投反对票。可能是因为这很容易使用谷歌找到? google.com.ar/…

标签: objective-c swift constraints nslayoutconstraint


【解决方案1】:
 let leftConstranint = NSLayoutConstraint(item: self.contentView, attribute: .Leading, relatedBy: .Equal, toItem: self.view, attribute: .Left, multiplier: 1.0, constant: 0)

 self.view.addConstraint(leftConstranint)

 let rightConstraint = NSLayoutConstraint(item: self.contentView, attribute: .Trailing, relatedBy: .Equal, toItem: self.view, attribute: .Right, multiplier: 1.0, constant: 0)

 self.view.addConstraint(rightConstraint)

.Leading.Left.Trailing.Right 是来自 NSLayoutAttribute 的枚举。 还有来自UIGestureRecognizerDelegate的函数:

func gestureRecognizerShouldBegin(gestureRecognizer: UIGestureRecognizer) -> Bool {
      return false
}

使用Cartography,您可以通过以下方式执行上述自动布局:

layout(self.contentView, self.view) { (contentView, view) -> () in
        contentView.leading == view.left
        contentView.trailing == view.right
 }

使用Snap,您可以在下面执行上述自动布局:

 self.contentView.snp_makeConstraints { maker in
        maker.leading.equalTo(self.view.snp_left)
        maker.trailing.equalTo(self.view.snp_right)
 }

Cartography 更像是一种数学方法,可以在代码中进行约束。换句话说,Snap 更像是一种英语语言方式来用文字描述您的约束。

与视觉语言格式(以纯字符串编码约束)不同,CartographySnap 都可以利用 XCode 中的代码完成功能。

【讨论】:

  • @iProgramIt,您也可以尝试一些第三方库以编程方式进行自动布局约束,例如CartographySnap。如果您发现我的回答解决了您的问题,您介意将其标记为已接受吗?
  • 我想知道苹果是否会考虑采用类似的方式。自动布局有帮助,但对于复杂的情况仍然很麻烦。 任何可以帮助开发人员处理的合理的事情都值得投资,IMO。
  • @Allaboutthatbase2 他们做了,它被称为 Interface Builder(不管喜欢与否)
  • @DepartamentoB MasonrySnap 是由同一个人开发的,他们几乎做同样的工作。但是Snap 是 Swift 唯一的库。
  • @DepartamentoB 是的,我知道这是 Apple 尝试处理具有多种屏幕尺寸、设备和方向的布局噩梦,而且我已经大量使用它。到目前为止,如果在 IB 中遇到麻烦,我需要做的就是在这里或那里调整屏幕,为一个约束创建一个出口,并根据屏幕变化和方向修改常量。但我说的是制图的便利性。苹果在哪里做了那个来帮助程序化方面的人们?他们会吗?
【解决方案2】:

使用 AutoLayout Visual Format Language 通常被认为是可取的:

var viewsDictionary = [ "contentView" : self.contentView, 
                        "view"        : self.view ]

var viewsConstraint = 
       NSLayoutConstraint.constraintsWithViaualFormat(
                     "[contentView][view]", 
                      options: 0, 
                      metrics: nil, 
                        views: viewsDictionary)
view.addConstraint(viewsConstraint)

但你也可以使用其他形式:

var leftConstraint = 
      NSLayoutConstraint(item: contentView,
                    attribute: .Leading, 
                    relatedBy: .Equal, 
                       toItem: view, 
                    attribute: .Left, 
                   multiplier: 1.0,
                     constant: 0)
view.addConstraint(leftConstraint)

var rightConstraint = 
      NSLayoutConstraint(item: contentView, 
                    attribute: .Trailing,
                    relatedBy: .Equal, 
                       toItem: view, 
                    attribute: .Right, 
                   multiplier: 1.0, 
                     constant: 0)
view.addConstraint(rightConstraint)

func gestureRecognizerShouldBegin(gestureRecognizer: UIGestureRecognizer) -> Bool {
  return false
}

【讨论】:

  • 感谢您的帮助。我更喜欢编写代码的第二个版本。 :)
  • @iProgramIt 第二种方式是到目前为止我在自己的代码中所做的所有事情,但是 Apple 和 Stack Overflow 上的其他开发人员以编程方式完成了很多自动布局,他们说 VFL 是去吧,所以我正在学习它。
  • CartographySnapVFL 相比,绝对可以帮助您编写更少的代码,而且您在使用字符串编写VFL 代码时很容易出错,而VFL 没有利用代码从 XCode 自动完成。
  • @ztan,我会检查一下。有时您可能想在算法上更改constantmultiplier,但我不确定如何使用VFL 干净轻松地做到这一点,但即使在一个源文件中也没有什么能阻止你使用混合。学习更多……但是 VFL 可以用更少的代码概括地表示复杂的结构,并使其更易于阅读和调整。这就是生活。一切都是为了在正确的时间做出正确的权衡。
  • @ztan, Cartography 看起来很方便!
猜你喜欢
  • 1970-01-01
  • 2018-04-08
  • 2016-01-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多