gpt4 book ai didi

macos - 使用 VFL 在 NSView 内部对齐 NSView

转载 作者:行者123 更新时间:2023-11-28 05:29:15 27 4
gpt4 key购买 nike

我有一个 NSView 的 subview (比如 MainView),里面有 NSTextField。

注意:此代码基于此 github.repo

MainView 有如下指定的初始化器

init(title : String, layout :NSLayoutAttribute) {
innerView = self.createTextField(title)//Text field with stringValue = title
mainView.addSubview(innerView)
createViewConstrants(innerView, layout: layout)
}

布局可以是LeftRightCenterX
(内部 TextView 将始终垂直居中,只有水平对齐可以变化)


下面的函数为目的做约束

func createViewConstrants(view : NSView, layout :NSLayoutAttribute) {

let viewMap = ["innerView" : view, "superview" : mainView]
var constraints :[AnyObject]!

switch layout {
case .Left:
println("Left")
constraints = NSLayoutConstraint.constraintsWithVisualFormat(
"H:[superview]-(<=1)-[innerView]",
options: NSLayoutFormatOptions.AlignAllCenterY,
metrics: nil,
views: viewMap)
mainView.addConstraints(constraints)

case .Right:
println("Right")
constraints = NSLayoutConstraint.constraintsWithVisualFormat(
"H:[superview]-(<=1)-[innerView]-|",
options: NSLayoutFormatOptions.AlignAllCenterY,
metrics: nil,
views: viewMap)
mainView.addConstraints(constraints)

case .CenterX:
println("Center")

constraints = NSLayoutConstraint.constraintsWithVisualFormat(
"V:[superview]-(<=1)-[innerView]",
options: NSLayoutFormatOptions.AlignAllCenterX,
metrics: nil,
views: viewMap)
mainView.addConstraints(constraints)

constraints = NSLayoutConstraint.constraintsWithVisualFormat(
"H:[superview]-(<=1)-[innerView]",
options: NSLayoutFormatOptions.AlignAllCenterY,
metrics: nil,
views: viewMap)
mainView.addConstraints(constraints)

default:
fatalError("Invalid layout")

}
}

Align RightCenter 工作正常,但 Align left 不工作。

此外,由于垂直居中对所有外壳都是通用的,可以将其从开关盒中取出吗?

最佳答案

几个问题:

  1. 您通常不会在 VFL 中显式列出父 View 。相反,您使用垂直线 (|) 字符。这:

    H:[superview]-(<=1)-[innerView]

    并不意味着 innerView 的前缘在父 View 的前缘“之后”不到 1 点。这意味着 innerView 的前沿距离父 View 的 trailing 边缘不到 1 点,这可能会将 innerView 置于其父 View 的边界之外,这会导致它被剪裁。

  2. 如果这些是您添加的影响 innerView 的唯一约束,那么您的布局是不明确的。不等式允许任何可能的值,并且系统没有可靠的方法来选择其中一个值而不是其他任何值。

  3. 您无法在 VFL 中真正表达居中。您可以将对齐标志传递给 constraintsWithVisualFormat(_:options:metrics:views:)(如您所知),但是 a) 这并不是视觉格式语言本身的一部分,并且 b ) 如果不在另一个方向上创建一些虚假的、不需要的约束,你就无法做到这一点。也就是说,除非您还创建了一些伪造的水平约束,否则您不能使用对齐标志来垂直居中。 (反之亦然。)这是因为对齐标志仅适用于 VFL 字符串中列出的 View ,而 VFL 字符串始终暗示约束。

  4. 为什么坚持使用VFL?如果您使用 init(item:attribute:relatedBy:toItem:attribute:multiplier:constant:),您可以简单地传递您的方法接收的 layout 参数。多个案例不需要 switch。你只需要做:

    var constraint = NSLayoutConstraint(item: innerView,
    attribute: layout,
    relatedBy: .Equal,
    toItem: mainView,
    attribute: layout
    multiplier: 1,
    constant: 0)
    mainView.addConstraint(constraint)
    constraint = NSLayoutConstraint(item: innerView,
    attribute: .CenterY,
    relatedBy: .Equal,
    toItem: mainView,
    attribute: .CenterY
    multiplier: 1,
    constant: 0)
    mainView.addConstraint(constraint)

    这将处理所有三种情况。

关于macos - 使用 VFL 在 NSView 内部对齐 NSView,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29577705/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com